1/* SPDX-License-Identifier: GPL-2.0+ */ 2/* 3 * arch/arm/cpu/armv8/rcar_gen3/lowlevel_init.S 4 * This file is lowlevel initialize routine. 5 * 6 * (C) Copyright 2015 Renesas Electronics Corporation 7 * 8 * This file is based on the arch/arm/cpu/armv8/start.S 9 * 10 * (C) Copyright 2013 11 * David Feng <fenghua@phytium.com.cn> 12 */ 13 14#include <asm-offsets.h> 15#include <config.h> 16#include <linux/linkage.h> 17#include <asm/macro.h> 18 19ENTRY(lowlevel_init) 20 mov x29, lr /* Save LR */ 21 22#ifndef CONFIG_ARMV8_MULTIENTRY 23 /* 24 * For single-entry systems the lowlevel init is very simple. 25 */ 26 ldr x0, =GICD_BASE 27 bl gic_init_secure 28 29#else /* CONFIG_ARMV8_MULTIENTRY is set */ 30 31#if defined(CONFIG_GICV2) || defined(CONFIG_GICV3) 32 branch_if_slave x0, 1f 33 ldr x0, =GICD_BASE 34 bl gic_init_secure 351: 36#if defined(CONFIG_GICV3) 37 ldr x0, =GICR_BASE 38 bl gic_init_secure_percpu 39#elif defined(CONFIG_GICV2) 40 ldr x0, =GICD_BASE 41 ldr x1, =GICC_BASE 42 bl gic_init_secure_percpu 43#endif 44#endif 45 46 branch_if_master x0, x1, 2f 47 48 /* 49 * Slave should wait for master clearing spin table. 50 * This sync prevent salves observing incorrect 51 * value of spin table and jumping to wrong place. 52 */ 53#if defined(CONFIG_GICV2) || defined(CONFIG_GICV3) 54#ifdef CONFIG_GICV2 55 ldr x0, =GICC_BASE 56#endif 57 bl gic_wait_for_interrupt 58#endif 59 60 /* 61 * All slaves will enter EL2 and optionally EL1. 62 */ 63 adr x4, lowlevel_in_el2 64 ldr x5, =ES_TO_AARCH64 65 bl armv8_switch_to_el2 66 67lowlevel_in_el2: 68#ifdef CONFIG_ARMV8_SWITCH_TO_EL1 69 adr x4, lowlevel_in_el1 70 ldr x5, =ES_TO_AARCH64 71 bl armv8_switch_to_el1 72 73lowlevel_in_el1: 74#endif 75#endif /* CONFIG_ARMV8_MULTIENTRY */ 76 77 bl s_init 78 792: 80 mov lr, x29 /* Restore LR */ 81 ret 82ENDPROC(lowlevel_init) 83