1/* 2 * Copyright (c) 2019-2022, Arm Limited. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7#include <arch.h> 8#include <asm_macros.S> 9#include <common/bl_common.h> 10#include <neoverse_v1.h> 11#include <cpu_macros.S> 12#include <plat_macros.S> 13#include "wa_cve_2022_23960_bhb_vector.S" 14 15/* Hardware handled coherency */ 16#if HW_ASSISTED_COHERENCY == 0 17#error "Neoverse V1 must be compiled with HW_ASSISTED_COHERENCY enabled" 18#endif 19 20/* 64-bit only core */ 21#if CTX_INCLUDE_AARCH32_REGS == 1 22#error "Neoverse-V1 supports only AArch64. Compile with CTX_INCLUDE_AARCH32_REGS=0" 23#endif 24 25#if WORKAROUND_CVE_2022_23960 26 wa_cve_2022_23960_bhb_vector_table NEOVERSE_V1_BHB_LOOP_COUNT, neoverse_v1 27#endif /* WORKAROUND_CVE_2022_23960 */ 28 29 /* -------------------------------------------------- 30 * Errata Workaround for Neoverse V1 Errata #1618635. 31 * This applies to revision r0p0 and is fixed in 32 * r1p0. 33 * x0: variant[4:7] and revision[0:3] of current cpu. 34 * Shall clobber: x0, x17 35 * -------------------------------------------------- 36 */ 37func errata_neoverse_v1_1618635_wa 38 /* Check workaround compatibility. */ 39 mov x17, x30 40 bl check_errata_1618635 41 cbz x0, 1f 42 43 /* Inserts a DMB SY before and after MRS PAR_EL1 */ 44 ldr x0, =0x0 45 msr NEOVERSE_V1_CPUPSELR_EL3, x0 46 ldr x0, = 0xEE070F14 47 msr NEOVERSE_V1_CPUPOR_EL3, x0 48 ldr x0, = 0xFFFF0FFF 49 msr NEOVERSE_V1_CPUPMR_EL3, x0 50 ldr x0, =0x4005027FF 51 msr NEOVERSE_V1_CPUPCR_EL3, x0 52 53 /* Inserts a DMB SY before STREX imm offset */ 54 ldr x0, =0x1 55 msr NEOVERSE_V1_CPUPSELR_EL3, x0 56 ldr x0, =0x00e8400000 57 msr NEOVERSE_V1_CPUPOR_EL3, x0 58 ldr x0, =0x00fff00000 59 msr NEOVERSE_V1_CPUPMR_EL3, x0 60 ldr x0, = 0x4001027FF 61 msr NEOVERSE_V1_CPUPCR_EL3, x0 62 63 /* Inserts a DMB SY before STREX[BHD}/STLEX* */ 64 ldr x0, =0x2 65 msr NEOVERSE_V1_CPUPSELR_EL3, x0 66 ldr x0, =0x00e8c00040 67 msr NEOVERSE_V1_CPUPOR_EL3, x0 68 ldr x0, =0x00fff00040 69 msr NEOVERSE_V1_CPUPMR_EL3, x0 70 ldr x0, = 0x4001027FF 71 msr NEOVERSE_V1_CPUPCR_EL3, x0 72 73 /* Inserts a DMB SY after STREX imm offset */ 74 ldr x0, =0x3 75 msr NEOVERSE_V1_CPUPSELR_EL3, x0 76 ldr x0, =0x00e8400000 77 msr NEOVERSE_V1_CPUPOR_EL3, x0 78 ldr x0, =0x00fff00000 79 msr NEOVERSE_V1_CPUPMR_EL3, x0 80 ldr x0, = 0x4004027FF 81 msr NEOVERSE_V1_CPUPCR_EL3, x0 82 83 /* Inserts a DMB SY after STREX[BHD}/STLEX* */ 84 ldr x0, =0x4 85 msr NEOVERSE_V1_CPUPSELR_EL3, x0 86 ldr x0, =0x00e8c00040 87 msr NEOVERSE_V1_CPUPOR_EL3, x0 88 ldr x0, =0x00fff00040 89 msr NEOVERSE_V1_CPUPMR_EL3, x0 90 ldr x0, = 0x4004027FF 91 msr NEOVERSE_V1_CPUPCR_EL3, x0 92 93 /* Synchronize to enable patches */ 94 isb 951: 96 ret x17 97endfunc errata_neoverse_v1_1618635_wa 98 99func check_errata_1618635 100 /* Applies to revision r0p0. */ 101 mov x1, #0x00 102 b cpu_rev_var_ls 103endfunc check_errata_1618635 104 105 /* -------------------------------------------------- 106 * Errata Workaround for Neoverse V1 Errata #1774420. 107 * This applies to revisions r0p0 and r1p0, fixed in r1p1. 108 * x0: variant[4:7] and revision[0:3] of current cpu. 109 * Shall clobber: x0-x17 110 * -------------------------------------------------- 111 */ 112func errata_neoverse_v1_1774420_wa 113 /* Check workaround compatibility. */ 114 mov x17, x30 115 bl check_errata_1774420 116 cbz x0, 1f 117 118 /* Set bit 53 in CPUECTLR_EL1 */ 119 mrs x1, NEOVERSE_V1_CPUECTLR_EL1 120 orr x1, x1, #NEOVERSE_V1_CPUECTLR_EL1_BIT_53 121 msr NEOVERSE_V1_CPUECTLR_EL1, x1 122 isb 1231: 124 ret x17 125endfunc errata_neoverse_v1_1774420_wa 126 127func check_errata_1774420 128 /* Applies to r0p0 and r1p0. */ 129 mov x1, #0x10 130 b cpu_rev_var_ls 131endfunc check_errata_1774420 132 133 /* -------------------------------------------------- 134 * Errata Workaround for Neoverse V1 Errata #1791573. 135 * This applies to revisions r0p0 and r1p0, fixed in r1p1. 136 * x0: variant[4:7] and revision[0:3] of current cpu. 137 * Shall clobber: x0-x17 138 * -------------------------------------------------- 139 */ 140func errata_neoverse_v1_1791573_wa 141 /* Check workaround compatibility. */ 142 mov x17, x30 143 bl check_errata_1791573 144 cbz x0, 1f 145 146 /* Set bit 2 in ACTLR2_EL1 */ 147 mrs x1, NEOVERSE_V1_ACTLR2_EL1 148 orr x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_2 149 msr NEOVERSE_V1_ACTLR2_EL1, x1 150 isb 1511: 152 ret x17 153endfunc errata_neoverse_v1_1791573_wa 154 155func check_errata_1791573 156 /* Applies to r0p0 and r1p0. */ 157 mov x1, #0x10 158 b cpu_rev_var_ls 159endfunc check_errata_1791573 160 161 /* -------------------------------------------------- 162 * Errata Workaround for Neoverse V1 Errata #1852267. 163 * This applies to revisions r0p0 and r1p0, fixed in r1p1. 164 * x0: variant[4:7] and revision[0:3] of current cpu. 165 * Shall clobber: x0-x17 166 * -------------------------------------------------- 167 */ 168func errata_neoverse_v1_1852267_wa 169 /* Check workaround compatibility. */ 170 mov x17, x30 171 bl check_errata_1852267 172 cbz x0, 1f 173 174 /* Set bit 28 in ACTLR2_EL1 */ 175 mrs x1, NEOVERSE_V1_ACTLR2_EL1 176 orr x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_28 177 msr NEOVERSE_V1_ACTLR2_EL1, x1 178 isb 1791: 180 ret x17 181endfunc errata_neoverse_v1_1852267_wa 182 183func check_errata_1852267 184 /* Applies to r0p0 and r1p0. */ 185 mov x1, #0x10 186 b cpu_rev_var_ls 187endfunc check_errata_1852267 188 189 /* -------------------------------------------------- 190 * Errata Workaround for Neoverse V1 Errata #1925756. 191 * This applies to revisions <= r1p1. 192 * x0: variant[4:7] and revision[0:3] of current cpu. 193 * Shall clobber: x0-x17 194 * -------------------------------------------------- 195 */ 196func errata_neoverse_v1_1925756_wa 197 /* Check workaround compatibility. */ 198 mov x17, x30 199 bl check_errata_1925756 200 cbz x0, 1f 201 202 /* Set bit 8 in CPUECTLR_EL1 */ 203 mrs x1, NEOVERSE_V1_CPUECTLR_EL1 204 orr x1, x1, #NEOVERSE_V1_CPUECTLR_EL1_BIT_8 205 msr NEOVERSE_V1_CPUECTLR_EL1, x1 206 isb 2071: 208 ret x17 209endfunc errata_neoverse_v1_1925756_wa 210 211func check_errata_1925756 212 /* Applies to <= r1p1. */ 213 mov x1, #0x11 214 b cpu_rev_var_ls 215endfunc check_errata_1925756 216 217 /* -------------------------------------------------- 218 * Errata Workaround for Neoverse V1 Erratum #1940577 219 * This applies to revisions r1p0 - r1p1 and is open. 220 * It also exists in r0p0 but there is no fix in that 221 * revision. 222 * Inputs: 223 * x0: variant[4:7] and revision[0:3] of current cpu. 224 * Shall clobber: x0-x17 225 * -------------------------------------------------- 226 */ 227func errata_neoverse_v1_1940577_wa 228 /* Compare x0 against revisions r1p0 - r1p1 */ 229 mov x17, x30 230 bl check_errata_1940577 231 cbz x0, 1f 232 233 mov x0, #0 234 msr S3_6_C15_C8_0, x0 235 ldr x0, =0x10E3900002 236 msr S3_6_C15_C8_2, x0 237 ldr x0, =0x10FFF00083 238 msr S3_6_C15_C8_3, x0 239 ldr x0, =0x2001003FF 240 msr S3_6_C15_C8_1, x0 241 242 mov x0, #1 243 msr S3_6_C15_C8_0, x0 244 ldr x0, =0x10E3800082 245 msr S3_6_C15_C8_2, x0 246 ldr x0, =0x10FFF00083 247 msr S3_6_C15_C8_3, x0 248 ldr x0, =0x2001003FF 249 msr S3_6_C15_C8_1, x0 250 251 mov x0, #2 252 msr S3_6_C15_C8_0, x0 253 ldr x0, =0x10E3800200 254 msr S3_6_C15_C8_2, x0 255 ldr x0, =0x10FFF003E0 256 msr S3_6_C15_C8_3, x0 257 ldr x0, =0x2001003FF 258 msr S3_6_C15_C8_1, x0 259 260 isb 2611: 262 ret x17 263endfunc errata_neoverse_v1_1940577_wa 264 265func check_errata_1940577 266 /* Applies to revisions r1p0 - r1p1. */ 267 mov x1, #0x10 268 mov x2, #0x11 269 b cpu_rev_var_range 270endfunc check_errata_1940577 271 272 /* -------------------------------------------------- 273 * Errata Workaround for Neoverse V1 Errata #1966096 274 * This applies to revisions r1p0 - r1p1 and is open. 275 * It also exists in r0p0 but there is no workaround 276 * for that revision. 277 * x0: variant[4:7] and revision[0:3] of current cpu. 278 * Shall clobber: x0-x17 279 * -------------------------------------------------- 280 */ 281func errata_neoverse_v1_1966096_wa 282 /* Check workaround compatibility. */ 283 mov x17, x30 284 bl check_errata_1966096 285 cbz x0, 1f 286 287 /* Apply the workaround. */ 288 mov x0, #0x3 289 msr S3_6_C15_C8_0, x0 290 ldr x0, =0xEE010F12 291 msr S3_6_C15_C8_2, x0 292 ldr x0, =0xFFFF0FFF 293 msr S3_6_C15_C8_3, x0 294 ldr x0, =0x80000000003FF 295 msr S3_6_C15_C8_1, x0 296 isb 297 2981: 299 ret x17 300endfunc errata_neoverse_v1_1966096_wa 301 302func check_errata_1966096 303 mov x1, #0x10 304 mov x2, #0x11 305 b cpu_rev_var_range 306endfunc check_errata_1966096 307 308 /* -------------------------------------------------- 309 * Errata Workaround for Neoverse V1 Errata #2139242. 310 * This applies to revisions r0p0, r1p0, and r1p1, it 311 * is still open. 312 * x0: variant[4:7] and revision[0:3] of current cpu. 313 * Shall clobber: x0-x17 314 * -------------------------------------------------- 315 */ 316func errata_neoverse_v1_2139242_wa 317 /* Check workaround compatibility. */ 318 mov x17, x30 319 bl check_errata_2139242 320 cbz x0, 1f 321 322 /* Apply the workaround. */ 323 mov x0, #0x3 324 msr S3_6_C15_C8_0, x0 325 ldr x0, =0xEE720F14 326 msr S3_6_C15_C8_2, x0 327 ldr x0, =0xFFFF0FDF 328 msr S3_6_C15_C8_3, x0 329 ldr x0, =0x40000005003FF 330 msr S3_6_C15_C8_1, x0 331 isb 332 3331: 334 ret x17 335endfunc errata_neoverse_v1_2139242_wa 336 337func check_errata_2139242 338 /* Applies to r0p0, r1p0, r1p1 */ 339 mov x1, #0x11 340 b cpu_rev_var_ls 341endfunc check_errata_2139242 342 343 /* -------------------------------------------------- 344 * Errata Workaround for Neoverse V1 Errata #2108267. 345 * This applies to revisions r0p0, r1p0, and r1p1, it 346 * is still open. 347 * x0: variant[4:7] and revision[0:3] of current cpu. 348 * Shall clobber: x0-x1, x17 349 * -------------------------------------------------- 350 */ 351func errata_neoverse_v1_2108267_wa 352 /* Check workaround compatibility. */ 353 mov x17, x30 354 bl check_errata_2108267 355 cbz x0, 1f 356 357 /* Apply the workaround. */ 358 mrs x1, NEOVERSE_V1_CPUECTLR_EL1 359 mov x0, #NEOVERSE_V1_CPUECTLR_EL1_PF_MODE_CNSRV 360 bfi x1, x0, #CPUECTLR_EL1_PF_MODE_LSB, #CPUECTLR_EL1_PF_MODE_WIDTH 361 msr NEOVERSE_V1_CPUECTLR_EL1, x1 3621: 363 ret x17 364endfunc errata_neoverse_v1_2108267_wa 365 366func check_errata_2108267 367 /* Applies to r0p0, r1p0, r1p1 */ 368 mov x1, #0x11 369 b cpu_rev_var_ls 370endfunc check_errata_2108267 371 372 /* -------------------------------------------------- 373 * Errata Workaround for Neoverse V1 Errata #2216392. 374 * This applies to revisions r1p0 and r1p1 and is 375 * still open. 376 * This issue is also present in r0p0 but there is no 377 * workaround in that revision. 378 * x0: variant[4:7] and revision[0:3] of current cpu. 379 * Shall clobber: x0-x17 380 * -------------------------------------------------- 381 */ 382func errata_neoverse_v1_2216392_wa 383 /* Check workaround compatibility. */ 384 mov x17, x30 385 bl check_errata_2216392 386 cbz x0, 1f 387 388 ldr x0, =0x5 389 msr S3_6_c15_c8_0, x0 /* CPUPSELR_EL3 */ 390 ldr x0, =0x10F600E000 391 msr S3_6_c15_c8_2, x0 /* CPUPOR_EL3 */ 392 ldr x0, =0x10FF80E000 393 msr S3_6_c15_c8_3, x0 /* CPUPMR_EL3 */ 394 ldr x0, =0x80000000003FF 395 msr S3_6_c15_c8_1, x0 /* CPUPCR_EL3 */ 396 397 isb 3981: 399 ret x17 400endfunc errata_neoverse_v1_2216392_wa 401 402func check_errata_2216392 403 /* Applies to revisions r1p0 and r1p1. */ 404 mov x1, #CPU_REV(1, 0) 405 mov x2, #CPU_REV(1, 1) 406 b cpu_rev_var_range 407endfunc check_errata_2216392 408 409 /* ----------------------------------------------------------------- 410 * Errata Workaround for Neoverse V1 Errata #2294912. 411 * This applies to revisions r0p0, r1p0, and r1p1 and is still open. 412 * x0: variant[4:7] and revision[0:3] of current cpu. 413 * Shall clobber: x0-x17 414 * ----------------------------------------------------------------- 415 */ 416func errata_neoverse_v1_2294912_wa 417 /* Check workaround compatibility. */ 418 mov x17, x30 419 bl check_errata_2294912 420 cbz x0, 1f 421 422 /* Set bit 0 in ACTLR2_EL1 */ 423 mrs x1, NEOVERSE_V1_ACTLR2_EL1 424 orr x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_0 425 msr NEOVERSE_V1_ACTLR2_EL1, x1 426 isb 4271: 428 ret x17 429endfunc errata_neoverse_v1_2294912_wa 430 431func check_errata_2294912 432 /* Applies to r0p0, r1p0, and r1p1 right now */ 433 mov x1, #0x11 434 b cpu_rev_var_ls 435endfunc check_errata_2294912 436 437 /* --------------------------------------------------- 438 * Errata Workaround for Neoverse V1 Errata #2372203. 439 * This applies to revisions <= r1p1 and is still open. 440 * x0: variant[4:7] and revision[0:3] of current cpu. 441 * Shall clobber: x0-x17 442 * ---------------------------------------------------- 443 */ 444func errata_neoverse_v1_2372203_wa 445 /* Check workaround compatibility. */ 446 mov x17, x30 447 bl check_errata_2372203 448 cbz x0, 1f 449 450 /* Set bit 40 in ACTLR2_EL1 */ 451 mrs x1, NEOVERSE_V1_ACTLR2_EL1 452 orr x1, x1, #NEOVERSE_V1_ACTLR2_EL1_BIT_40 453 msr NEOVERSE_V1_ACTLR2_EL1, x1 454 isb 4551: 456 ret x17 457endfunc errata_neoverse_v1_2372203_wa 458 459func check_errata_2372203 460 /* Applies to <= r1p1. */ 461 mov x1, #0x11 462 b cpu_rev_var_ls 463endfunc check_errata_2372203 464 465func check_errata_cve_2022_23960 466#if WORKAROUND_CVE_2022_23960 467 mov x0, #ERRATA_APPLIES 468#else 469 mov x0, #ERRATA_MISSING 470#endif 471 ret 472endfunc check_errata_cve_2022_23960 473 474 /* --------------------------------------------- 475 * HW will do the cache maintenance while powering down 476 * --------------------------------------------- 477 */ 478func neoverse_v1_core_pwr_dwn 479 /* --------------------------------------------- 480 * Enable CPU power down bit in power control register 481 * --------------------------------------------- 482 */ 483 mrs x0, NEOVERSE_V1_CPUPWRCTLR_EL1 484 orr x0, x0, #NEOVERSE_V1_CPUPWRCTLR_EL1_CORE_PWRDN_BIT 485 msr NEOVERSE_V1_CPUPWRCTLR_EL1, x0 486 isb 487 ret 488endfunc neoverse_v1_core_pwr_dwn 489 490 /* 491 * Errata printing function for Neoverse V1. Must follow AAPCS. 492 */ 493#if REPORT_ERRATA 494func neoverse_v1_errata_report 495 stp x8, x30, [sp, #-16]! 496 497 bl cpu_get_rev_var 498 mov x8, x0 499 500 /* 501 * Report all errata. The revision-variant information is passed to 502 * checking functions of each errata. 503 */ 504 report_errata ERRATA_V1_1618635, neoverse_v1, 1618635 505 report_errata ERRATA_V1_1774420, neoverse_v1, 1774420 506 report_errata ERRATA_V1_1791573, neoverse_v1, 1791573 507 report_errata ERRATA_V1_1852267, neoverse_v1, 1852267 508 report_errata ERRATA_V1_1925756, neoverse_v1, 1925756 509 report_errata ERRATA_V1_1940577, neoverse_v1, 1940577 510 report_errata ERRATA_V1_1966096, neoverse_v1, 1966096 511 report_errata ERRATA_V1_2108267, neoverse_v1, 2108267 512 report_errata ERRATA_V1_2139242, neoverse_v1, 2139242 513 report_errata ERRATA_V1_2216392, neoverse_v1, 2216392 514 report_errata ERRATA_V1_2294912, neoverse_v1, 2294912 515 report_errata ERRATA_V1_2372203, neoverse_v1, 2372203 516 report_errata WORKAROUND_CVE_2022_23960, neoverse_v1, cve_2022_23960 517 518 ldp x8, x30, [sp], #16 519 ret 520endfunc neoverse_v1_errata_report 521#endif 522 523func neoverse_v1_reset_func 524 mov x19, x30 525 526 /* Disable speculative loads */ 527 msr SSBS, xzr 528 isb 529 530 /* Get the CPU revision and stash it in x18. */ 531 bl cpu_get_rev_var 532 mov x18, x0 533 534#if ERRATA_V1_1618635 535 mov x0, x18 536 bl errata_neoverse_v1_1618635_wa 537#endif 538 539#if ERRATA_V1_1774420 540 mov x0, x18 541 bl errata_neoverse_v1_1774420_wa 542#endif 543 544#if ERRATA_V1_1791573 545 mov x0, x18 546 bl errata_neoverse_v1_1791573_wa 547#endif 548 549#if ERRATA_V1_1852267 550 mov x0, x18 551 bl errata_neoverse_v1_1852267_wa 552#endif 553 554#if ERRATA_V1_1925756 555 mov x0, x18 556 bl errata_neoverse_v1_1925756_wa 557#endif 558 559#if ERRATA_V1_1940577 560 mov x0, x18 561 bl errata_neoverse_v1_1940577_wa 562#endif 563 564#if ERRATA_V1_1966096 565 mov x0, x18 566 bl errata_neoverse_v1_1966096_wa 567#endif 568 569#if ERRATA_V1_2139242 570 mov x0, x18 571 bl errata_neoverse_v1_2139242_wa 572#endif 573 574#if ERRATA_V1_2108267 575 mov x0, x18 576 bl errata_neoverse_v1_2108267_wa 577#endif 578 579#if ERRATA_V1_2216392 580 mov x0, x18 581 bl errata_neoverse_v1_2216392_wa 582#endif 583 584#if ERRATA_V1_2294912 585 mov x0, x18 586 bl errata_neoverse_v1_2294912_wa 587#endif 588 589#if ERRATA_V1_2372203 590 mov x0, x18 591 bl errata_neoverse_v1_2372203_wa 592#endif 593 594#if IMAGE_BL31 && WORKAROUND_CVE_2022_23960 595 /* 596 * The Neoverse-V1 generic vectors are overridden to apply errata 597 * mitigation on exception entry from lower ELs. 598 */ 599 adr x0, wa_cve_vbar_neoverse_v1 600 msr vbar_el3, x0 601#endif /* IMAGE_BL31 && WORKAROUND_CVE_2022_23960 */ 602 603 isb 604 ret x19 605endfunc neoverse_v1_reset_func 606 607 /* --------------------------------------------- 608 * This function provides Neoverse-V1 specific 609 * register information for crash reporting. 610 * It needs to return with x6 pointing to 611 * a list of register names in ascii and 612 * x8 - x15 having values of registers to be 613 * reported. 614 * --------------------------------------------- 615 */ 616.section .rodata.neoverse_v1_regs, "aS" 617neoverse_v1_regs: /* The ascii list of register names to be reported */ 618 .asciz "cpuectlr_el1", "" 619 620func neoverse_v1_cpu_reg_dump 621 adr x6, neoverse_v1_regs 622 mrs x8, NEOVERSE_V1_CPUECTLR_EL1 623 ret 624endfunc neoverse_v1_cpu_reg_dump 625 626declare_cpu_ops neoverse_v1, NEOVERSE_V1_MIDR, \ 627 neoverse_v1_reset_func, \ 628 neoverse_v1_core_pwr_dwn 629