123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106 |
- /*
- * GIC Initialization Routines.
- *
- * (C) Copyright 2013
- * David Feng <fenghua@phytium.com.cn>
- *
- * SPDX-License-Identifier: GPL-2.0+
- */
- #include <asm-offsets.h>
- #include <config.h>
- #include <linux/linkage.h>
- #include <asm/macro.h>
- #include <asm/gic.h>
- /*************************************************************************
- *
- * void gic_init(void) __attribute__((weak));
- *
- * Currently, this routine only initialize secure copy of GIC
- * with Security Extensions at EL3.
- *
- *************************************************************************/
- WEAK(gic_init)
- branch_if_slave x0, 2f
- /* Initialize Distributor and SPIs */
- ldr x1, =GICD_BASE
- mov w0, #0x3 /* EnableGrp0 | EnableGrp1 */
- str w0, [x1, GICD_CTLR] /* Secure GICD_CTLR */
- ldr w0, [x1, GICD_TYPER]
- and w2, w0, #0x1f /* ITLinesNumber */
- cbz w2, 2f /* No SPIs */
- add x1, x1, (GICD_IGROUPRn + 4)
- mov w0, #~0 /* Config SPIs as Grp1 */
- 1: str w0, [x1], #0x4
- sub w2, w2, #0x1
- cbnz w2, 1b
- /* Initialize SGIs and PPIs */
- 2: ldr x1, =GICD_BASE
- mov w0, #~0 /* Config SGIs and PPIs as Grp1 */
- str w0, [x1, GICD_IGROUPRn] /* GICD_IGROUPR0 */
- mov w0, #0x1 /* Enable SGI 0 */
- str w0, [x1, GICD_ISENABLERn]
- /* Initialize Cpu Interface */
- ldr x1, =GICC_BASE
- mov w0, #0x1e7 /* Disable IRQ/FIQ Bypass & */
- /* Enable Ack Group1 Interrupt & */
- /* EnableGrp0 & EnableGrp1 */
- str w0, [x1, GICC_CTLR] /* Secure GICC_CTLR */
- mov w0, #0x1 << 7 /* Non-Secure access to GICC_PMR */
- str w0, [x1, GICC_PMR]
- ret
- ENDPROC(gic_init)
- /*************************************************************************
- *
- * void gic_send_sgi(u64 sgi) __attribute__((weak));
- *
- *************************************************************************/
- WEAK(gic_send_sgi)
- ldr x1, =GICD_BASE
- mov w2, #0x8000
- movk w2, #0x100, lsl #16
- orr w2, w2, w0
- str w2, [x1, GICD_SGIR]
- ret
- ENDPROC(gic_send_sgi)
- /*************************************************************************
- *
- * void wait_for_wakeup(void) __attribute__((weak));
- *
- * Wait for SGI 0 from master.
- *
- *************************************************************************/
- WEAK(wait_for_wakeup)
- ldr x1, =GICC_BASE
- 0: wfi
- ldr w0, [x1, GICC_AIAR]
- str w0, [x1, GICC_AEOIR]
- cbnz w0, 0b
- ret
- ENDPROC(wait_for_wakeup)
- /*************************************************************************
- *
- * void smp_kick_all_cpus(void) __attribute__((weak));
- *
- *************************************************************************/
- WEAK(smp_kick_all_cpus)
- /* Kick secondary cpus up by SGI 0 interrupt */
- mov x0, xzr /* SGI 0 */
- mov x29, lr /* Save LR */
- bl gic_send_sgi
- mov lr, x29 /* Restore LR */
- ret
- ENDPROC(smp_kick_all_cpus)
|