1 /* 2 * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7 #ifndef __GICV3_PRIVATE_H__ 8 #define __GICV3_PRIVATE_H__ 9 10 #include <assert.h> 11 #include <gic_common.h> 12 #include <gicv3.h> 13 #include <mmio.h> 14 #include <stdint.h> 15 #include "../common/gic_common_private.h" 16 17 /******************************************************************************* 18 * GICv3 private macro definitions 19 ******************************************************************************/ 20 21 /* Constants to indicate the status of the RWP bit */ 22 #define RWP_TRUE 1 23 #define RWP_FALSE 0 24 25 /* 26 * Macro to convert an mpidr to a value suitable for programming into a 27 * GICD_IROUTER. Bits[31:24] in the MPIDR are cleared as they are not relevant 28 * to GICv3. 29 */ 30 #define gicd_irouter_val_from_mpidr(mpidr, irm) \ 31 ((mpidr & ~(0xff << 24)) | \ 32 (irm & IROUTER_IRM_MASK) << IROUTER_IRM_SHIFT) 33 34 /* 35 * Macro to convert a GICR_TYPER affinity value into a MPIDR value. Bits[31:24] 36 * are zeroes. 37 */ 38 #ifdef AARCH32 39 #define mpidr_from_gicr_typer(typer_val) (((typer_val) >> 32) & 0xffffff) 40 #else 41 #define mpidr_from_gicr_typer(typer_val) \ 42 (((((typer_val) >> 56) & MPIDR_AFFLVL_MASK) << MPIDR_AFF3_SHIFT) | \ 43 (((typer_val) >> 32) & 0xffffff)) 44 #endif 45 46 /******************************************************************************* 47 * GICv3 private global variables declarations 48 ******************************************************************************/ 49 extern const gicv3_driver_data_t *gicv3_driver_data; 50 51 /******************************************************************************* 52 * Private GICv3 function prototypes for accessing entire registers. 53 * Note: The raw register values correspond to multiple interrupt IDs and 54 * the number of interrupt IDs involved depends on the register accessed. 55 ******************************************************************************/ 56 unsigned int gicd_read_igrpmodr(uintptr_t base, unsigned int id); 57 unsigned int gicr_read_ipriorityr(uintptr_t base, unsigned int id); 58 void gicd_write_igrpmodr(uintptr_t base, unsigned int id, unsigned int val); 59 void gicr_write_ipriorityr(uintptr_t base, unsigned int id, unsigned int val); 60 61 /******************************************************************************* 62 * Private GICv3 function prototypes for accessing the GIC registers 63 * corresponding to a single interrupt ID. These functions use bitwise 64 * operations or appropriate register accesses to modify or return 65 * the bit-field corresponding the single interrupt ID. 66 ******************************************************************************/ 67 unsigned int gicd_get_igrpmodr(uintptr_t base, unsigned int id); 68 unsigned int gicr_get_igrpmodr0(uintptr_t base, unsigned int id); 69 unsigned int gicr_get_igroupr0(uintptr_t base, unsigned int id); 70 unsigned int gicr_get_isactiver0(uintptr_t base, unsigned int id); 71 void gicd_set_igrpmodr(uintptr_t base, unsigned int id); 72 void gicr_set_igrpmodr0(uintptr_t base, unsigned int id); 73 void gicr_set_isenabler0(uintptr_t base, unsigned int id); 74 void gicr_set_icenabler0(uintptr_t base, unsigned int id); 75 void gicr_set_ispendr0(uintptr_t base, unsigned int id); 76 void gicr_set_icpendr0(uintptr_t base, unsigned int id); 77 void gicr_set_igroupr0(uintptr_t base, unsigned int id); 78 void gicd_clr_igrpmodr(uintptr_t base, unsigned int id); 79 void gicr_clr_igrpmodr0(uintptr_t base, unsigned int id); 80 void gicr_clr_igroupr0(uintptr_t base, unsigned int id); 81 void gicr_set_ipriorityr(uintptr_t base, unsigned int id, unsigned int pri); 82 83 /******************************************************************************* 84 * Private GICv3 helper function prototypes 85 ******************************************************************************/ 86 void gicv3_spis_configure_defaults(uintptr_t gicd_base); 87 void gicv3_ppi_sgi_configure_defaults(uintptr_t gicr_base); 88 void gicv3_secure_spis_configure(uintptr_t gicd_base, 89 unsigned int num_ints, 90 const unsigned int *sec_intr_list, 91 unsigned int int_grp); 92 void gicv3_secure_ppi_sgi_configure(uintptr_t gicr_base, 93 unsigned int num_ints, 94 const unsigned int *sec_intr_list, 95 unsigned int int_grp); 96 void gicv3_rdistif_base_addrs_probe(uintptr_t *rdistif_base_addrs, 97 unsigned int rdistif_num, 98 uintptr_t gicr_base, 99 mpidr_hash_fn mpidr_to_core_pos); 100 void gicv3_rdistif_mark_core_awake(uintptr_t gicr_base); 101 void gicv3_rdistif_mark_core_asleep(uintptr_t gicr_base); 102 103 /******************************************************************************* 104 * GIC Distributor interface accessors 105 ******************************************************************************/ 106 /* 107 * Wait for updates to : 108 * GICD_CTLR[2:0] - the Group Enables 109 * GICD_CTLR[5:4] - the ARE bits 110 * GICD_ICENABLERn - the clearing of enable state for SPIs 111 */ 112 static inline void gicd_wait_for_pending_write(uintptr_t gicd_base) 113 { 114 while (gicd_read_ctlr(gicd_base) & GICD_CTLR_RWP_BIT) 115 ; 116 } 117 118 static inline unsigned int gicd_read_pidr2(uintptr_t base) 119 { 120 return mmio_read_32(base + GICD_PIDR2_GICV3); 121 } 122 123 static inline unsigned long long gicd_read_irouter(uintptr_t base, unsigned int id) 124 { 125 assert(id >= MIN_SPI_ID); 126 return mmio_read_64(base + GICD_IROUTER + (id << 3)); 127 } 128 129 static inline void gicd_write_irouter(uintptr_t base, 130 unsigned int id, 131 unsigned long long affinity) 132 { 133 assert(id >= MIN_SPI_ID); 134 mmio_write_64(base + GICD_IROUTER + (id << 3), affinity); 135 } 136 137 static inline void gicd_clr_ctlr(uintptr_t base, 138 unsigned int bitmap, 139 unsigned int rwp) 140 { 141 gicd_write_ctlr(base, gicd_read_ctlr(base) & ~bitmap); 142 if (rwp) 143 gicd_wait_for_pending_write(base); 144 } 145 146 static inline void gicd_set_ctlr(uintptr_t base, 147 unsigned int bitmap, 148 unsigned int rwp) 149 { 150 gicd_write_ctlr(base, gicd_read_ctlr(base) | bitmap); 151 if (rwp) 152 gicd_wait_for_pending_write(base); 153 } 154 155 /******************************************************************************* 156 * GIC Redistributor interface accessors 157 ******************************************************************************/ 158 static inline unsigned long long gicr_read_ctlr(uintptr_t base) 159 { 160 return mmio_read_64(base + GICR_CTLR); 161 } 162 163 static inline void gicr_write_ctlr(uintptr_t base, uint64_t val) 164 { 165 mmio_write_64(base + GICR_CTLR, val); 166 } 167 168 static inline unsigned long long gicr_read_typer(uintptr_t base) 169 { 170 return mmio_read_64(base + GICR_TYPER); 171 } 172 173 static inline unsigned int gicr_read_waker(uintptr_t base) 174 { 175 return mmio_read_32(base + GICR_WAKER); 176 } 177 178 static inline void gicr_write_waker(uintptr_t base, unsigned int val) 179 { 180 mmio_write_32(base + GICR_WAKER, val); 181 } 182 183 /* 184 * Wait for updates to : 185 * GICR_ICENABLER0 186 * GICR_CTLR.DPG1S 187 * GICR_CTLR.DPG1NS 188 * GICR_CTLR.DPG0 189 */ 190 static inline void gicr_wait_for_pending_write(uintptr_t gicr_base) 191 { 192 while (gicr_read_ctlr(gicr_base) & GICR_CTLR_RWP_BIT) 193 ; 194 } 195 196 static inline void gicr_wait_for_upstream_pending_write(uintptr_t gicr_base) 197 { 198 while (gicr_read_ctlr(gicr_base) & GICR_CTLR_UWP_BIT) 199 ; 200 } 201 202 /* Private implementation of Distributor power control hooks */ 203 void arm_gicv3_distif_pre_save(unsigned int rdist_proc_num); 204 void arm_gicv3_distif_post_restore(unsigned int rdist_proc_num); 205 206 /******************************************************************************* 207 * GIC Re-distributor functions for accessing entire registers. 208 * Note: The raw register values correspond to multiple interrupt IDs and 209 * the number of interrupt IDs involved depends on the register accessed. 210 ******************************************************************************/ 211 static inline unsigned int gicr_read_icenabler0(uintptr_t base) 212 { 213 return mmio_read_32(base + GICR_ICENABLER0); 214 } 215 216 static inline void gicr_write_icenabler0(uintptr_t base, unsigned int val) 217 { 218 mmio_write_32(base + GICR_ICENABLER0, val); 219 } 220 221 static inline unsigned int gicr_read_isenabler0(uintptr_t base) 222 { 223 return mmio_read_32(base + GICR_ISENABLER0); 224 } 225 226 static inline void gicr_write_icpendr0(uintptr_t base, unsigned int val) 227 { 228 mmio_write_32(base + GICR_ICPENDR0, val); 229 } 230 231 static inline void gicr_write_isenabler0(uintptr_t base, unsigned int val) 232 { 233 mmio_write_32(base + GICR_ISENABLER0, val); 234 } 235 236 static inline unsigned int gicr_read_igroupr0(uintptr_t base) 237 { 238 return mmio_read_32(base + GICR_IGROUPR0); 239 } 240 241 static inline unsigned int gicr_read_ispendr0(uintptr_t base) 242 { 243 return mmio_read_32(base + GICR_ISPENDR0); 244 } 245 246 static inline void gicr_write_ispendr0(uintptr_t base, unsigned int val) 247 { 248 mmio_write_32(base + GICR_ISPENDR0, val); 249 } 250 251 static inline void gicr_write_igroupr0(uintptr_t base, unsigned int val) 252 { 253 mmio_write_32(base + GICR_IGROUPR0, val); 254 } 255 256 static inline unsigned int gicr_read_igrpmodr0(uintptr_t base) 257 { 258 return mmio_read_32(base + GICR_IGRPMODR0); 259 } 260 261 static inline void gicr_write_igrpmodr0(uintptr_t base, unsigned int val) 262 { 263 mmio_write_32(base + GICR_IGRPMODR0, val); 264 } 265 266 static inline unsigned int gicr_read_nsacr(uintptr_t base) 267 { 268 return mmio_read_32(base + GICR_NSACR); 269 } 270 271 static inline void gicr_write_nsacr(uintptr_t base, unsigned int val) 272 { 273 mmio_write_32(base + GICR_NSACR, val); 274 } 275 276 static inline unsigned int gicr_read_isactiver0(uintptr_t base) 277 { 278 return mmio_read_32(base + GICR_ISACTIVER0); 279 } 280 281 static inline void gicr_write_isactiver0(uintptr_t base, unsigned int val) 282 { 283 mmio_write_32(base + GICR_ISACTIVER0, val); 284 } 285 286 static inline unsigned int gicr_read_icfgr0(uintptr_t base) 287 { 288 return mmio_read_32(base + GICR_ICFGR0); 289 } 290 291 static inline unsigned int gicr_read_icfgr1(uintptr_t base) 292 { 293 return mmio_read_32(base + GICR_ICFGR1); 294 } 295 296 static inline void gicr_write_icfgr0(uintptr_t base, unsigned int val) 297 { 298 mmio_write_32(base + GICR_ICFGR0, val); 299 } 300 301 static inline void gicr_write_icfgr1(uintptr_t base, unsigned int val) 302 { 303 mmio_write_32(base + GICR_ICFGR1, val); 304 } 305 306 static inline unsigned int gicr_read_propbaser(uintptr_t base) 307 { 308 return mmio_read_32(base + GICR_PROPBASER); 309 } 310 311 static inline void gicr_write_propbaser(uintptr_t base, unsigned int val) 312 { 313 mmio_write_32(base + GICR_PROPBASER, val); 314 } 315 316 static inline unsigned int gicr_read_pendbaser(uintptr_t base) 317 { 318 return mmio_read_32(base + GICR_PENDBASER); 319 } 320 321 static inline void gicr_write_pendbaser(uintptr_t base, unsigned int val) 322 { 323 mmio_write_32(base + GICR_PENDBASER, val); 324 } 325 326 /******************************************************************************* 327 * GIC ITS functions to read and write entire ITS registers. 328 ******************************************************************************/ 329 static inline uint32_t gits_read_ctlr(uintptr_t base) 330 { 331 return mmio_read_32(base + GITS_CTLR); 332 } 333 334 static inline void gits_write_ctlr(uintptr_t base, unsigned int val) 335 { 336 mmio_write_32(base + GITS_CTLR, val); 337 } 338 339 static inline uint64_t gits_read_cbaser(uintptr_t base) 340 { 341 return mmio_read_64(base + GITS_CBASER); 342 } 343 344 static inline void gits_write_cbaser(uintptr_t base, uint64_t val) 345 { 346 mmio_write_32(base + GITS_CBASER, val); 347 } 348 349 static inline uint64_t gits_read_cwriter(uintptr_t base) 350 { 351 return mmio_read_64(base + GITS_CWRITER); 352 } 353 354 static inline void gits_write_cwriter(uintptr_t base, uint64_t val) 355 { 356 mmio_write_32(base + GITS_CWRITER, val); 357 } 358 359 static inline uint64_t gits_read_baser(uintptr_t base, unsigned int its_table_id) 360 { 361 assert(its_table_id < 8); 362 return mmio_read_64(base + GITS_BASER + (8 * its_table_id)); 363 } 364 365 static inline void gits_write_baser(uintptr_t base, unsigned int its_table_id, uint64_t val) 366 { 367 assert(its_table_id < 8); 368 mmio_write_64(base + GITS_BASER + (8 * its_table_id), val); 369 } 370 371 /* 372 * Wait for Quiescent bit when GIC ITS is disabled 373 */ 374 static inline void gits_wait_for_quiescent_bit(uintptr_t gits_base) 375 { 376 assert(!(gits_read_ctlr(gits_base) & GITS_CTLR_ENABLED_BIT)); 377 while ((gits_read_ctlr(gits_base) & GITS_CTLR_QUIESCENT_BIT) == 0) 378 ; 379 } 380 381 382 #endif /* __GICV3_PRIVATE_H__ */ 383