xref: /rk3399_ARM-atf/include/drivers/arm/gicv5.h (revision dfb37a2df579ccf0e92c97515452b13ce2c9fba8)
1 /*
2  * Copyright (c) 2025, Arm Limited and Contributors. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #ifndef GICV5_H
8 #define GICV5_H
9 
10 #ifndef __ASSEMBLER__
11 #include <stdbool.h>
12 #include <stdint.h>
13 
14 #include <lib/mmio.h>
15 #endif
16 
17 #include <lib/utils_def.h>
18 
19 /* Interrupt Domain definitions */
20 #define INTDMN_S				0
21 #define INTDMN_NS				1
22 #define INTDMN_EL3				2
23 #define INTDMN_RL				3
24 
25 /* Trigger modes */
26 #define TM_EDGE					0
27 #define TM_LEVEL				1
28 
29 /* Architected PPI numbers */
30 #define PPI_TRBIRQ				31
31 #define PPI_CNTP				30
32 #define PPI_CNTPS				29
33 #define PPI_CNTHV				28
34 #define PPI_CNTV				27
35 #define PPI_CNTHP				26
36 #define PPI_GICMNT				25
37 #define PPI_CTIIRQ				24
38 #define PPI_PMUIRQ				23
39 #define PPI_COMMIRQ				22
40 #define PPI_PMBIRQ				21
41 #define PPI_CNTHPS				20
42 #define PPI_CNTHVS				19
43 #define PPI_DB_NS				2
44 #define PPI_DB_RL				1
45 #define PPI_DB_S				0
46 
47 /* IRS register fields */
48 #define IRS_IDR6_SPI_IRS_RANGE_SHIFT		0
49 #define IRS_IDR6_SPI_IRS_RANGE_WIDTH		24
50 #define IRS_IDR7_SPI_BASE_SHIFT			0
51 #define IRS_IDR7_SPI_BASE_WIDTH			24
52 
53 #define IRS_SPI_STATUSR_IDLE_BIT		BIT(0)
54 #define IRS_SPI_STATUSR_V_BIT			BIT(1)
55 
56 #ifndef __ASSEMBLER__
57 
58 #define _PPI_FIELD_SHIFT(_REG, _ppi_id)						\
59 	((_ppi_id % (ICC_PPI_##_REG##_COUNT)) * (64 / ICC_PPI_##_REG##_COUNT))
60 
61 #define write_icc_ppi_domainr(_var, _ppi_id, _value)				\
62 	do {									\
63 		_var |=  (uint64_t)_value << _PPI_FIELD_SHIFT(DOMAINR, _ppi_id);\
64 	} while (false)
65 
66 
67 #define DEFINE_GICV5_MMIO_WRITE_FUNC(_name, _offset)				\
68 static inline void write_##_name(uintptr_t base, uint32_t val)			\
69 {										\
70 	mmio_write_32(base + _offset, val);					\
71 }
72 
73 #define DEFINE_GICV5_MMIO_READ_FUNC(_name, _offset)				\
74 static inline uint32_t read_##_name(uintptr_t base)				\
75 {										\
76 	return mmio_read_32(base + _offset);					\
77 }
78 
79 #define DEFINE_GICV5_MMIO_RW_FUNCS(_name, _offset)				\
80 	DEFINE_GICV5_MMIO_READ_FUNC(_name, _offset)				\
81 	DEFINE_GICV5_MMIO_WRITE_FUNC(_name, _offset)
82 
83 DEFINE_GICV5_MMIO_READ_FUNC(irs_idr6,			0x0018)
84 DEFINE_GICV5_MMIO_READ_FUNC(irs_idr7,			0x001c)
85 DEFINE_GICV5_MMIO_RW_FUNCS( irs_spi_selr,		0x0108)
86 DEFINE_GICV5_MMIO_RW_FUNCS( irs_spi_domainr,		0x010c)
87 DEFINE_GICV5_MMIO_RW_FUNCS( irs_spi_cfgr,		0x0114)
88 DEFINE_GICV5_MMIO_READ_FUNC(irs_spi_statusr,		0x0118)
89 
90 #define WAIT_FOR_IDLE(base, reg, reg_up)					\
91 	do {									\
92 		while ((read_##reg(base) & reg_up##_IDLE_BIT) == 0U) {}		\
93 	} while (0)
94 
95 /* wait for IDLE but also check the V bit was set */
96 #define WAIT_FOR_VIDLE(base, reg, reg_up)					\
97 	do {									\
98 		uint32_t val;							\
99 		while (((val = read_##reg(base)) & reg_up##_IDLE_BIT) == 0U) {}	\
100 		assert((val & reg##_V_BIT) != 0U);				\
101 	} while (0)
102 
103 #define WAIT_FOR_VIDLE_IRS_SPI_STATUSR(base)					\
104 	WAIT_FOR_IDLE(base, irs_spi_statusr, IRS_SPI_STATUSR)
105 
106 struct gicv5_wire_props {
107 	/* continuous wire ID as seen by the attached component */
108 	uint32_t id;
109 	/* use the INTDMN_XYZ macros */
110 	uint8_t domain:2;
111 	/* use the TM_XYZ (eg. TM_EDGE) macros */
112 	uint8_t tm:1;
113 };
114 
115 /* to describe every IRS in the system */
116 struct gicv5_irs {
117 	/* mapped device nGnRnE by the platform*/
118 	uintptr_t el3_config_frame;
119 	struct gicv5_wire_props *spis;
120 	uint32_t num_spis;
121 };
122 
123 struct gicv5_driver_data {
124 	struct gicv5_irs *irss;
125 	uint32_t num_irss;
126 };
127 
128 extern const struct gicv5_driver_data plat_gicv5_driver_data;
129 
130 void gicv5_driver_init();
131 uint8_t gicv5_get_pending_interrupt_type(void);
132 bool gicv5_has_interrupt_type(unsigned int type);
133 void gicv5_enable_ppis();
134 #endif /* __ASSEMBLER__ */
135 #endif /* GICV5_H */
136