diff options
Diffstat (limited to 'include/drivers/arm/gic_v2.h')
-rw-r--r-- | include/drivers/arm/gic_v2.h | 216 |
1 files changed, 106 insertions, 110 deletions
diff --git a/include/drivers/arm/gic_v2.h b/include/drivers/arm/gic_v2.h index e375566..271538f 100644 --- a/include/drivers/arm/gic_v2.h +++ b/include/drivers/arm/gic_v2.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2013-2014, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2013-2016, ARM Limited and Contributors. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: @@ -31,58 +31,29 @@ #ifndef __GIC_V2_H__ #define __GIC_V2_H__ -#define GIC400_NUM_SPIS 480 -#define MAX_PPIS 14 -#define MAX_SGIS 16 -#define GIC_MAX_CPU_INTERFACES 8 - -#define MIN_SGI_ID 0 -#define MAX_SGI_ID 15 -#define MIN_PPI_ID 16 -#define MAX_PPI_ID 31 -#define MIN_SPI_ID 32 - -#define GIC_PRI_MASK 0xff -#define GIC_HIGHEST_NS_PRIORITY 0 -#define GIC_LOWEST_NS_PRIORITY 254 /* 255 would disable an interrupt */ -#define GIC_SPURIOUS_INTERRUPT 1023 - -/* Distributor interface definitions */ -#define GICD_CTLR 0x0 -#define GICD_TYPER 0x4 -#define GICD_ISENABLER 0x100 -#define GICD_ICENABLER 0x180 -#define GICD_ISPENDR 0x200 -#define GICD_ICPENDR 0x280 -#define GICD_ISACTIVER 0x300 -#define GICD_ICACTIVER 0x380 -#define GICD_IPRIORITYR 0x400 +/*************************************************************************** + * Defines and prototypes specific to GIC v2. + **************************************************************************/ + +/* GICD_CTLR bit definitions */ +#define GICD_CTLR_ENABLE (1 << 0) + +/* Distributor interface register offsets */ #define GICD_ITARGETSR 0x800 -#define GICD_ICFGR 0xC00 #define GICD_SGIR 0xF00 #define GICD_CPENDSGIR 0xF10 #define GICD_SPENDSGIR 0xF20 -/* GICD_CTLR bit definitions */ -#define GICD_CTLR_ENABLE (1 << 0) - -#define ISENABLER_SHIFT 5 -#define ICENABLER_SHIFT ISENABLER_SHIFT -#define ISPENDR_SHIFT 5 -#define PEND_IRQS_PER_REG 32 -#define ICPENDR_SHIFT ISPENDR_SHIFT -#define ISACTIVER_SHIFT 5 -#define ICACTIVER_SHIFT ISACTIVER_SHIFT -#define IPRIORITYR_SHIFT 2 +/* GIC Distributor register shifts */ #define ITARGETSR_SHIFT 2 -#define ICFGR_SHIFT 4 #define CPENDSGIR_SHIFT 2 #define SPENDSGIR_SHIFT CPENDSGIR_SHIFT -/* GICD_TYPER bit definitions */ -#define IT_LINES_NO_MASK 0x1f +/* GICD_SGIR bit shifts */ +#define GICD_SGIR_INTID_SHIFT 0 +#define GICD_SGIR_CPUTL_SHIFT 16 -/* Physical CPU Interface registers */ +/* Physical CPU Interface register offsets */ #define GICC_CTLR 0x0 #define GICC_PMR 0x4 #define GICC_BPR 0x8 @@ -93,7 +64,7 @@ #define GICC_AHPPIR 0x28 #define GICC_IIDR 0xFC #define GICC_DIR 0x1000 -#define GICC_PRIODROP GICC_EOIR +#define GICC_PRIODROP GICC_EOIR /* GICC_IIDR bit masks and shifts */ #define GICC_IIDR_PID_SHIFT 20 @@ -106,7 +77,7 @@ #define GICC_IIDR_REV_MASK 0xf #define GICC_IIDR_IMP_MASK 0xfff -/* HYP view virtual CPU Interface registers */ +/* HYP view virtual CPU Interface register offsets */ #define GICH_CTL 0x0 #define GICH_VTR 0x4 #define GICH_ELRSR0 0x30 @@ -114,7 +85,7 @@ #define GICH_APR0 0xF0 #define GICH_LR_BASE 0x100 -/* Virtual CPU Interface registers */ +/* Virtual CPU Interface register offsets */ #define GICV_CTL 0x0 #define GICV_PRIMASK 0x4 #define GICV_BP 0x8 @@ -124,10 +95,6 @@ #define GICV_HIGHESTPEND 0x18 #define GICV_DEACTIVATE 0x1000 -/* GICD_SGIR bit shifts */ -#define GICD_SGIR_INTID_SHIFT 0 -#define GICD_SGIR_CPUTL_SHIFT 16 - /* GICC_IAR bit masks and shifts */ #define GICC_IAR_INTID_SHIFT 0 #define GICC_IAR_CPUID_SHIFT 10 @@ -155,74 +122,24 @@ #include <mmio.h> /******************************************************************************* - * GIC Distributor function prototypes + * Private Interfaces for internal use by the GICv2 driver ******************************************************************************/ -unsigned int gicd_read_isenabler(unsigned int, unsigned int); -unsigned int gicd_read_icenabler(unsigned int, unsigned int); -unsigned int gicd_read_ispendr(unsigned int, unsigned int); -unsigned int gicd_read_icpendr(unsigned int, unsigned int); -unsigned int gicd_read_isactiver(unsigned int, unsigned int); -unsigned int gicd_read_icactiver(unsigned int, unsigned int); -unsigned int gicd_read_ipriorityr(unsigned int, unsigned int); -unsigned int gicd_read_itargetsr(unsigned int, unsigned int); -unsigned int gicd_read_icfgr(unsigned int, unsigned int); -unsigned int gicd_read_cpendsgir(unsigned int, unsigned int); -unsigned int gicd_read_spendsgir(unsigned int, unsigned int); -void gicd_write_isenabler(unsigned int, unsigned int, unsigned int); -void gicd_write_icenabler(unsigned int, unsigned int, unsigned int); -void gicd_write_ispendr(unsigned int, unsigned int, unsigned int); -void gicd_write_icpendr(unsigned int, unsigned int, unsigned int); -void gicd_write_isactiver(unsigned int, unsigned int, unsigned int); -void gicd_write_icactiver(unsigned int, unsigned int, unsigned int); -void gicd_write_ipriorityr(unsigned int, unsigned int, unsigned int); -void gicd_write_itargetsr(unsigned int, unsigned int, unsigned int); -void gicd_write_icfgr(unsigned int, unsigned int, unsigned int); -void gicd_write_cpendsgir(unsigned int, unsigned int, unsigned int); -void gicd_write_spendsgir(unsigned int, unsigned int, unsigned int); -void gicd_set_isenabler(unsigned int, unsigned int); -void gicd_set_icenabler(unsigned int, unsigned int); -void gicd_set_ispendr(unsigned int, unsigned int); -void gicd_set_icpendr(unsigned int, unsigned int); -void gicd_set_isactiver(unsigned int, unsigned int); -void gicd_set_icactiver(unsigned int, unsigned int); -void gicd_set_ipriorityr(unsigned int, unsigned int, unsigned int); -void gicd_set_itargetsr(unsigned int, unsigned int, unsigned int); -void gicd_clear_itargetsr(unsigned int, unsigned int, unsigned int); /******************************************************************************* - * GIC Distributor interface accessors for reading entire registers + * GICv2 Distributor interface accessors for reading/writing entire registers ******************************************************************************/ -static inline unsigned int gicd_read_ctlr(unsigned int base) -{ - return mmio_read_32(base + GICD_CTLR); -} - -static inline unsigned int gicd_read_typer(unsigned int base) -{ - return mmio_read_32(base + GICD_TYPER); -} - static inline unsigned int gicd_read_sgir(unsigned int base) { return mmio_read_32(base + GICD_SGIR); } -/******************************************************************************* - * GIC Distributor interface accessors for writing entire registers - ******************************************************************************/ -static inline void gicd_write_ctlr(unsigned int base, unsigned int val) -{ - mmio_write_32(base + GICD_CTLR, val); -} - static inline void gicd_write_sgir(unsigned int base, unsigned int val) { mmio_write_32(base + GICD_SGIR, val); } - /******************************************************************************* - * GIC CPU interface accessors for reading entire registers + * GICv2 CPU interface accessors for reading entire registers ******************************************************************************/ static inline unsigned int gicc_read_ctlr(unsigned int base) @@ -272,7 +189,7 @@ static inline unsigned int gicc_read_iidr(unsigned int base) /******************************************************************************* - * GIC CPU interface accessors for writing entire registers + * GICv2 CPU interface accessors for writing entire registers ******************************************************************************/ static inline void gicc_write_ctlr(unsigned int base, unsigned int val) @@ -311,12 +228,91 @@ static inline void gicc_write_dir(unsigned int base, unsigned int val) mmio_write_32(base + GICC_DIR, val); } -/******************************************************************************* - * Prototype of function to map an interrupt type to the interrupt line used to - * signal it. - ******************************************************************************/ -uint32_t gicv2_interrupt_type_to_line(uint32_t cpuif_base, uint32_t type); +/****************************************************************************** + * GICv2 public driver API + *****************************************************************************/ -#endif /*__ASSEMBLY__*/ +/* + * Initialize the GICv2 driver. The base addresses of GIC CPU interface + * `gicc_base` and the Distributor interface `gicd_base` must be provided + * as arguments. + */ +void gicv2_init(uintptr_t gicc_base, uintptr_t gicd_base); + +/* + * Write the GICv2 EOIR register with `val` passed as argument. `val` + * should be the raw value read from IAR register. + */ +void gicv2_gicc_write_eoir(unsigned int val); +/* + * Set the bit corresponding to `interrupt_id` in the GICD ICPENDR register. + */ +void gicv2_gicd_set_icpendr(unsigned int interrupt_id); + +/* + * Get the bit corresponding to `interrupt_id` from the GICD ISPENDR register. + */ +unsigned int gicv2_gicd_get_ispendr(unsigned int interrupt_id); + +/* + * Read and return the value in GICC IAR register + */ +unsigned int gicv2_gicc_read_iar(void); + +/* + * Set the bit corresponding to `num` in the GICD ICENABLER register. + */ +void gicv2_gicd_set_icenabler(unsigned int num); + +/* + * Set the bit corresponding to `num` in the GICD ISENABLER register. + */ +void gicv2_gicd_set_isenabler(unsigned int num); + +/* + * Set the target of interrupt ID `num` to core with index `core_pos`. + */ +void gicv2_set_itargetsr(unsigned int num, unsigned int core_pos); + +/* + * Send SGI with ID `sgi_id` to core with index `core_pos`. + */ +void gicv2_send_sgi(unsigned int sgi_id, unsigned int core_pos); + +/* + * Set the priority of the interrupt `interrupt_id` to `priority`. + */ +void gicv2_gicd_set_ipriorityr(unsigned int interrupt_id, unsigned int priority); + +/* + * Setup the GIC Distributor interface. + */ +void gicv2_setup_distif(void); + +/* + * Disable the GIC CPU interface. + */ +void gicv2_disable_cpuif(void); + +/* + * Setup the GIC CPU interface. + */ +void gicv2_setup_cpuif(void); + +/* + * Enable the GIC CPU interface. + */ +void gicv2_enable_cpuif(void); + +/* + * Read the GICD ITARGETR0 to figure out the GIC ID for the current core. + * This function is required to be invoked on successful boot of a core. + * The GIC ID will be stored internally by the driver to convert core index + * to GIC CPU ID when required. + */ +void gicv2_probe_gic_cpu_id(void); + + +#endif /*__ASSEMBLY__*/ #endif /* __GIC_V2_H__ */ |