qemu/target/riscv/csr.c
<<
>>
Prefs
   1/*
   2 * RISC-V Control and Status Registers.
   3 *
   4 * Copyright (c) 2016-2017 Sagar Karandikar, sagark@eecs.berkeley.edu
   5 * Copyright (c) 2017-2018 SiFive, Inc.
   6 *
   7 * This program is free software; you can redistribute it and/or modify it
   8 * under the terms and conditions of the GNU General Public License,
   9 * version 2 or later, as published by the Free Software Foundation.
  10 *
  11 * This program is distributed in the hope it will be useful, but WITHOUT
  12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
  14 * more details.
  15 *
  16 * You should have received a copy of the GNU General Public License along with
  17 * this program.  If not, see <http://www.gnu.org/licenses/>.
  18 */
  19
  20#include "qemu/osdep.h"
  21#include "qemu/log.h"
  22#include "qemu/timer.h"
  23#include "cpu.h"
  24#include "pmu.h"
  25#include "time_helper.h"
  26#include "qemu/main-loop.h"
  27#include "exec/exec-all.h"
  28#include "exec/tb-flush.h"
  29#include "sysemu/cpu-timers.h"
  30#include "qemu/guest-random.h"
  31#include "qapi/error.h"
  32
  33/* CSR function table public API */
  34void riscv_get_csr_ops(int csrno, riscv_csr_operations *ops)
  35{
  36    *ops = csr_ops[csrno & (CSR_TABLE_SIZE - 1)];
  37}
  38
  39void riscv_set_csr_ops(int csrno, riscv_csr_operations *ops)
  40{
  41    csr_ops[csrno & (CSR_TABLE_SIZE - 1)] = *ops;
  42}
  43
  44/* Predicates */
  45#if !defined(CONFIG_USER_ONLY)
  46static RISCVException smstateen_acc_ok(CPURISCVState *env, int index,
  47                                       uint64_t bit)
  48{
  49    bool virt = riscv_cpu_virt_enabled(env);
  50
  51    if (env->priv == PRV_M || !riscv_cpu_cfg(env)->ext_smstateen) {
  52        return RISCV_EXCP_NONE;
  53    }
  54
  55    if (!(env->mstateen[index] & bit)) {
  56        return RISCV_EXCP_ILLEGAL_INST;
  57    }
  58
  59    if (virt) {
  60        if (!(env->hstateen[index] & bit)) {
  61            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
  62        }
  63
  64        if (env->priv == PRV_U && !(env->sstateen[index] & bit)) {
  65            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
  66        }
  67    }
  68
  69    if (env->priv == PRV_U && riscv_has_ext(env, RVS)) {
  70        if (!(env->sstateen[index] & bit)) {
  71            return RISCV_EXCP_ILLEGAL_INST;
  72        }
  73    }
  74
  75    return RISCV_EXCP_NONE;
  76}
  77#endif
  78
  79static RISCVException fs(CPURISCVState *env, int csrno)
  80{
  81#if !defined(CONFIG_USER_ONLY)
  82    if (!env->debugger && !riscv_cpu_fp_enabled(env) &&
  83        !riscv_cpu_cfg(env)->ext_zfinx) {
  84        return RISCV_EXCP_ILLEGAL_INST;
  85    }
  86#endif
  87    return RISCV_EXCP_NONE;
  88}
  89
  90static RISCVException vs(CPURISCVState *env, int csrno)
  91{
  92    RISCVCPU *cpu = env_archcpu(env);
  93
  94    if (cpu->cfg.ext_zve32f) {
  95#if !defined(CONFIG_USER_ONLY)
  96        if (!env->debugger && !riscv_cpu_vector_enabled(env)) {
  97            return RISCV_EXCP_ILLEGAL_INST;
  98        }
  99#endif
 100        return RISCV_EXCP_NONE;
 101    }
 102    return RISCV_EXCP_ILLEGAL_INST;
 103}
 104
 105static RISCVException ctr(CPURISCVState *env, int csrno)
 106{
 107#if !defined(CONFIG_USER_ONLY)
 108    RISCVCPU *cpu = env_archcpu(env);
 109    int ctr_index;
 110    target_ulong ctr_mask;
 111    int base_csrno = CSR_CYCLE;
 112    bool rv32 = riscv_cpu_mxl(env) == MXL_RV32 ? true : false;
 113
 114    if (rv32 && csrno >= CSR_CYCLEH) {
 115        /* Offset for RV32 hpmcounternh counters */
 116        base_csrno += 0x80;
 117    }
 118    ctr_index = csrno - base_csrno;
 119    ctr_mask = BIT(ctr_index);
 120
 121    if ((csrno >= CSR_CYCLE && csrno <= CSR_INSTRET) ||
 122        (csrno >= CSR_CYCLEH && csrno <= CSR_INSTRETH)) {
 123        goto skip_ext_pmu_check;
 124    }
 125
 126    if (!(cpu->pmu_avail_ctrs & ctr_mask)) {
 127        /* No counter is enabled in PMU or the counter is out of range */
 128        return RISCV_EXCP_ILLEGAL_INST;
 129    }
 130
 131skip_ext_pmu_check:
 132
 133    if (env->debugger) {
 134        return RISCV_EXCP_NONE;
 135    }
 136
 137    if (env->priv < PRV_M && !get_field(env->mcounteren, ctr_mask)) {
 138        return RISCV_EXCP_ILLEGAL_INST;
 139    }
 140
 141    if (riscv_cpu_virt_enabled(env)) {
 142        if (!get_field(env->hcounteren, ctr_mask) ||
 143            (env->priv == PRV_U && !get_field(env->scounteren, ctr_mask))) {
 144            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
 145        }
 146    }
 147
 148    if (riscv_has_ext(env, RVS) && env->priv == PRV_U &&
 149        !get_field(env->scounteren, ctr_mask)) {
 150        return RISCV_EXCP_ILLEGAL_INST;
 151    }
 152
 153#endif
 154    return RISCV_EXCP_NONE;
 155}
 156
 157static RISCVException ctr32(CPURISCVState *env, int csrno)
 158{
 159    if (riscv_cpu_mxl(env) != MXL_RV32) {
 160        return RISCV_EXCP_ILLEGAL_INST;
 161    }
 162
 163    return ctr(env, csrno);
 164}
 165
 166#if !defined(CONFIG_USER_ONLY)
 167static RISCVException mctr(CPURISCVState *env, int csrno)
 168{
 169    int pmu_num = riscv_cpu_cfg(env)->pmu_num;
 170    int ctr_index;
 171    int base_csrno = CSR_MHPMCOUNTER3;
 172
 173    if ((riscv_cpu_mxl(env) == MXL_RV32) && csrno >= CSR_MCYCLEH) {
 174        /* Offset for RV32 mhpmcounternh counters */
 175        base_csrno += 0x80;
 176    }
 177    ctr_index = csrno - base_csrno;
 178    if (!pmu_num || ctr_index >= pmu_num) {
 179        /* The PMU is not enabled or counter is out of range*/
 180        return RISCV_EXCP_ILLEGAL_INST;
 181    }
 182
 183    return RISCV_EXCP_NONE;
 184}
 185
 186static RISCVException mctr32(CPURISCVState *env, int csrno)
 187{
 188    if (riscv_cpu_mxl(env) != MXL_RV32) {
 189        return RISCV_EXCP_ILLEGAL_INST;
 190    }
 191
 192    return mctr(env, csrno);
 193}
 194
 195static RISCVException sscofpmf(CPURISCVState *env, int csrno)
 196{
 197    RISCVCPU *cpu = env_archcpu(env);
 198
 199    if (!cpu->cfg.ext_sscofpmf) {
 200        return RISCV_EXCP_ILLEGAL_INST;
 201    }
 202
 203    return RISCV_EXCP_NONE;
 204}
 205
 206static RISCVException any(CPURISCVState *env, int csrno)
 207{
 208    return RISCV_EXCP_NONE;
 209}
 210
 211static RISCVException any32(CPURISCVState *env, int csrno)
 212{
 213    if (riscv_cpu_mxl(env) != MXL_RV32) {
 214        return RISCV_EXCP_ILLEGAL_INST;
 215    }
 216
 217    return any(env, csrno);
 218
 219}
 220
 221static int aia_any(CPURISCVState *env, int csrno)
 222{
 223    if (!riscv_cpu_cfg(env)->ext_smaia) {
 224        return RISCV_EXCP_ILLEGAL_INST;
 225    }
 226
 227    return any(env, csrno);
 228}
 229
 230static int aia_any32(CPURISCVState *env, int csrno)
 231{
 232    if (!riscv_cpu_cfg(env)->ext_smaia) {
 233        return RISCV_EXCP_ILLEGAL_INST;
 234    }
 235
 236    return any32(env, csrno);
 237}
 238
 239static RISCVException smode(CPURISCVState *env, int csrno)
 240{
 241    if (riscv_has_ext(env, RVS)) {
 242        return RISCV_EXCP_NONE;
 243    }
 244
 245    return RISCV_EXCP_ILLEGAL_INST;
 246}
 247
 248static int smode32(CPURISCVState *env, int csrno)
 249{
 250    if (riscv_cpu_mxl(env) != MXL_RV32) {
 251        return RISCV_EXCP_ILLEGAL_INST;
 252    }
 253
 254    return smode(env, csrno);
 255}
 256
 257static int aia_smode(CPURISCVState *env, int csrno)
 258{
 259    if (!riscv_cpu_cfg(env)->ext_ssaia) {
 260        return RISCV_EXCP_ILLEGAL_INST;
 261    }
 262
 263    return smode(env, csrno);
 264}
 265
 266static int aia_smode32(CPURISCVState *env, int csrno)
 267{
 268    if (!riscv_cpu_cfg(env)->ext_ssaia) {
 269        return RISCV_EXCP_ILLEGAL_INST;
 270    }
 271
 272    return smode32(env, csrno);
 273}
 274
 275static RISCVException hmode(CPURISCVState *env, int csrno)
 276{
 277    if (riscv_has_ext(env, RVH)) {
 278        return RISCV_EXCP_NONE;
 279    }
 280
 281    return RISCV_EXCP_ILLEGAL_INST;
 282}
 283
 284static RISCVException hmode32(CPURISCVState *env, int csrno)
 285{
 286    if (riscv_cpu_mxl(env) != MXL_RV32) {
 287        return RISCV_EXCP_ILLEGAL_INST;
 288    }
 289
 290    return hmode(env, csrno);
 291
 292}
 293
 294static RISCVException umode(CPURISCVState *env, int csrno)
 295{
 296    if (riscv_has_ext(env, RVU)) {
 297        return RISCV_EXCP_NONE;
 298    }
 299
 300    return RISCV_EXCP_ILLEGAL_INST;
 301}
 302
 303static RISCVException umode32(CPURISCVState *env, int csrno)
 304{
 305    if (riscv_cpu_mxl(env) != MXL_RV32) {
 306        return RISCV_EXCP_ILLEGAL_INST;
 307    }
 308
 309    return umode(env, csrno);
 310}
 311
 312static RISCVException mstateen(CPURISCVState *env, int csrno)
 313{
 314    RISCVCPU *cpu = env_archcpu(env);
 315
 316    if (!cpu->cfg.ext_smstateen) {
 317        return RISCV_EXCP_ILLEGAL_INST;
 318    }
 319
 320    return any(env, csrno);
 321}
 322
 323static RISCVException hstateen_pred(CPURISCVState *env, int csrno, int base)
 324{
 325    RISCVCPU *cpu = env_archcpu(env);
 326
 327    if (!cpu->cfg.ext_smstateen) {
 328        return RISCV_EXCP_ILLEGAL_INST;
 329    }
 330
 331    RISCVException ret = hmode(env, csrno);
 332    if (ret != RISCV_EXCP_NONE) {
 333        return ret;
 334    }
 335
 336    if (env->debugger) {
 337        return RISCV_EXCP_NONE;
 338    }
 339
 340    if (env->priv < PRV_M) {
 341        if (!(env->mstateen[csrno - base] & SMSTATEEN_STATEEN)) {
 342            return RISCV_EXCP_ILLEGAL_INST;
 343        }
 344    }
 345
 346    return RISCV_EXCP_NONE;
 347}
 348
 349static RISCVException hstateen(CPURISCVState *env, int csrno)
 350{
 351    return hstateen_pred(env, csrno, CSR_HSTATEEN0);
 352}
 353
 354static RISCVException hstateenh(CPURISCVState *env, int csrno)
 355{
 356    return hstateen_pred(env, csrno, CSR_HSTATEEN0H);
 357}
 358
 359static RISCVException sstateen(CPURISCVState *env, int csrno)
 360{
 361    bool virt = riscv_cpu_virt_enabled(env);
 362    int index = csrno - CSR_SSTATEEN0;
 363
 364    if (!riscv_cpu_cfg(env)->ext_smstateen) {
 365        return RISCV_EXCP_ILLEGAL_INST;
 366    }
 367
 368    RISCVException ret = smode(env, csrno);
 369    if (ret != RISCV_EXCP_NONE) {
 370        return ret;
 371    }
 372
 373    if (env->debugger) {
 374        return RISCV_EXCP_NONE;
 375    }
 376
 377    if (env->priv < PRV_M) {
 378        if (!(env->mstateen[index] & SMSTATEEN_STATEEN)) {
 379            return RISCV_EXCP_ILLEGAL_INST;
 380        }
 381
 382        if (virt) {
 383            if (!(env->hstateen[index] & SMSTATEEN_STATEEN)) {
 384                return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
 385            }
 386        }
 387    }
 388
 389    return RISCV_EXCP_NONE;
 390}
 391
 392static RISCVException sstc(CPURISCVState *env, int csrno)
 393{
 394    RISCVCPU *cpu = env_archcpu(env);
 395    bool hmode_check = false;
 396
 397    if (!cpu->cfg.ext_sstc || !env->rdtime_fn) {
 398        return RISCV_EXCP_ILLEGAL_INST;
 399    }
 400
 401    if ((csrno == CSR_VSTIMECMP) || (csrno == CSR_VSTIMECMPH)) {
 402        hmode_check = true;
 403    }
 404
 405    RISCVException ret = hmode_check ? hmode(env, csrno) : smode(env, csrno);
 406    if (ret != RISCV_EXCP_NONE) {
 407        return ret;
 408    }
 409
 410    if (env->debugger) {
 411        return RISCV_EXCP_NONE;
 412    }
 413
 414    if (env->priv == PRV_M) {
 415        return RISCV_EXCP_NONE;
 416    }
 417
 418    /*
 419     * No need of separate function for rv32 as menvcfg stores both menvcfg
 420     * menvcfgh for RV32.
 421     */
 422    if (!(get_field(env->mcounteren, COUNTEREN_TM) &&
 423          get_field(env->menvcfg, MENVCFG_STCE))) {
 424        return RISCV_EXCP_ILLEGAL_INST;
 425    }
 426
 427    if (riscv_cpu_virt_enabled(env)) {
 428        if (!(get_field(env->hcounteren, COUNTEREN_TM) &&
 429              get_field(env->henvcfg, HENVCFG_STCE))) {
 430            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
 431        }
 432    }
 433
 434    return RISCV_EXCP_NONE;
 435}
 436
 437static RISCVException sstc_32(CPURISCVState *env, int csrno)
 438{
 439    if (riscv_cpu_mxl(env) != MXL_RV32) {
 440        return RISCV_EXCP_ILLEGAL_INST;
 441    }
 442
 443    return sstc(env, csrno);
 444}
 445
 446/* Checks if PointerMasking registers could be accessed */
 447static RISCVException pointer_masking(CPURISCVState *env, int csrno)
 448{
 449    /* Check if j-ext is present */
 450    if (riscv_has_ext(env, RVJ)) {
 451        return RISCV_EXCP_NONE;
 452    }
 453    return RISCV_EXCP_ILLEGAL_INST;
 454}
 455
 456static int aia_hmode(CPURISCVState *env, int csrno)
 457{
 458    if (!riscv_cpu_cfg(env)->ext_ssaia) {
 459        return RISCV_EXCP_ILLEGAL_INST;
 460     }
 461
 462     return hmode(env, csrno);
 463}
 464
 465static int aia_hmode32(CPURISCVState *env, int csrno)
 466{
 467    if (!riscv_cpu_cfg(env)->ext_ssaia) {
 468        return RISCV_EXCP_ILLEGAL_INST;
 469    }
 470
 471    return hmode32(env, csrno);
 472}
 473
 474static RISCVException pmp(CPURISCVState *env, int csrno)
 475{
 476    if (riscv_cpu_cfg(env)->pmp) {
 477        if (csrno <= CSR_PMPCFG3) {
 478            uint32_t reg_index = csrno - CSR_PMPCFG0;
 479
 480            /* TODO: RV128 restriction check */
 481            if ((reg_index & 1) && (riscv_cpu_mxl(env) == MXL_RV64)) {
 482                return RISCV_EXCP_ILLEGAL_INST;
 483            }
 484        }
 485
 486        return RISCV_EXCP_NONE;
 487    }
 488
 489    return RISCV_EXCP_ILLEGAL_INST;
 490}
 491
 492static RISCVException epmp(CPURISCVState *env, int csrno)
 493{
 494    if (riscv_cpu_cfg(env)->epmp) {
 495        return RISCV_EXCP_NONE;
 496    }
 497
 498    return RISCV_EXCP_ILLEGAL_INST;
 499}
 500
 501static RISCVException debug(CPURISCVState *env, int csrno)
 502{
 503    if (riscv_cpu_cfg(env)->debug) {
 504        return RISCV_EXCP_NONE;
 505    }
 506
 507    return RISCV_EXCP_ILLEGAL_INST;
 508}
 509#endif
 510
 511static RISCVException seed(CPURISCVState *env, int csrno)
 512{
 513    if (!riscv_cpu_cfg(env)->ext_zkr) {
 514        return RISCV_EXCP_ILLEGAL_INST;
 515    }
 516
 517#if !defined(CONFIG_USER_ONLY)
 518    if (env->debugger) {
 519        return RISCV_EXCP_NONE;
 520    }
 521
 522    /*
 523     * With a CSR read-write instruction:
 524     * 1) The seed CSR is always available in machine mode as normal.
 525     * 2) Attempted access to seed from virtual modes VS and VU always raises
 526     * an exception(virtual instruction exception only if mseccfg.sseed=1).
 527     * 3) Without the corresponding access control bit set to 1, any attempted
 528     * access to seed from U, S or HS modes will raise an illegal instruction
 529     * exception.
 530     */
 531    if (env->priv == PRV_M) {
 532        return RISCV_EXCP_NONE;
 533    } else if (riscv_cpu_virt_enabled(env)) {
 534        if (env->mseccfg & MSECCFG_SSEED) {
 535            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
 536        } else {
 537            return RISCV_EXCP_ILLEGAL_INST;
 538        }
 539    } else {
 540        if (env->priv == PRV_S && (env->mseccfg & MSECCFG_SSEED)) {
 541            return RISCV_EXCP_NONE;
 542        } else if (env->priv == PRV_U && (env->mseccfg & MSECCFG_USEED)) {
 543            return RISCV_EXCP_NONE;
 544        } else {
 545            return RISCV_EXCP_ILLEGAL_INST;
 546        }
 547    }
 548#else
 549    return RISCV_EXCP_NONE;
 550#endif
 551}
 552
 553/* User Floating-Point CSRs */
 554static RISCVException read_fflags(CPURISCVState *env, int csrno,
 555                                  target_ulong *val)
 556{
 557    *val = riscv_cpu_get_fflags(env);
 558    return RISCV_EXCP_NONE;
 559}
 560
 561static RISCVException write_fflags(CPURISCVState *env, int csrno,
 562                                   target_ulong val)
 563{
 564#if !defined(CONFIG_USER_ONLY)
 565    if (riscv_has_ext(env, RVF)) {
 566        env->mstatus |= MSTATUS_FS;
 567    }
 568#endif
 569    riscv_cpu_set_fflags(env, val & (FSR_AEXC >> FSR_AEXC_SHIFT));
 570    return RISCV_EXCP_NONE;
 571}
 572
 573static RISCVException read_frm(CPURISCVState *env, int csrno,
 574                               target_ulong *val)
 575{
 576    *val = env->frm;
 577    return RISCV_EXCP_NONE;
 578}
 579
 580static RISCVException write_frm(CPURISCVState *env, int csrno,
 581                                target_ulong val)
 582{
 583#if !defined(CONFIG_USER_ONLY)
 584    if (riscv_has_ext(env, RVF)) {
 585        env->mstatus |= MSTATUS_FS;
 586    }
 587#endif
 588    env->frm = val & (FSR_RD >> FSR_RD_SHIFT);
 589    return RISCV_EXCP_NONE;
 590}
 591
 592static RISCVException read_fcsr(CPURISCVState *env, int csrno,
 593                                target_ulong *val)
 594{
 595    *val = (riscv_cpu_get_fflags(env) << FSR_AEXC_SHIFT)
 596        | (env->frm << FSR_RD_SHIFT);
 597    return RISCV_EXCP_NONE;
 598}
 599
 600static RISCVException write_fcsr(CPURISCVState *env, int csrno,
 601                                 target_ulong val)
 602{
 603#if !defined(CONFIG_USER_ONLY)
 604    if (riscv_has_ext(env, RVF)) {
 605        env->mstatus |= MSTATUS_FS;
 606    }
 607#endif
 608    env->frm = (val & FSR_RD) >> FSR_RD_SHIFT;
 609    riscv_cpu_set_fflags(env, (val & FSR_AEXC) >> FSR_AEXC_SHIFT);
 610    return RISCV_EXCP_NONE;
 611}
 612
 613static RISCVException read_vtype(CPURISCVState *env, int csrno,
 614                                 target_ulong *val)
 615{
 616    uint64_t vill;
 617    switch (env->xl) {
 618    case MXL_RV32:
 619        vill = (uint32_t)env->vill << 31;
 620        break;
 621    case MXL_RV64:
 622        vill = (uint64_t)env->vill << 63;
 623        break;
 624    default:
 625        g_assert_not_reached();
 626    }
 627    *val = (target_ulong)vill | env->vtype;
 628    return RISCV_EXCP_NONE;
 629}
 630
 631static RISCVException read_vl(CPURISCVState *env, int csrno,
 632                              target_ulong *val)
 633{
 634    *val = env->vl;
 635    return RISCV_EXCP_NONE;
 636}
 637
 638static int read_vlenb(CPURISCVState *env, int csrno, target_ulong *val)
 639{
 640    *val = riscv_cpu_cfg(env)->vlen >> 3;
 641    return RISCV_EXCP_NONE;
 642}
 643
 644static RISCVException read_vxrm(CPURISCVState *env, int csrno,
 645                                target_ulong *val)
 646{
 647    *val = env->vxrm;
 648    return RISCV_EXCP_NONE;
 649}
 650
 651static RISCVException write_vxrm(CPURISCVState *env, int csrno,
 652                                 target_ulong val)
 653{
 654#if !defined(CONFIG_USER_ONLY)
 655    env->mstatus |= MSTATUS_VS;
 656#endif
 657    env->vxrm = val;
 658    return RISCV_EXCP_NONE;
 659}
 660
 661static RISCVException read_vxsat(CPURISCVState *env, int csrno,
 662                                 target_ulong *val)
 663{
 664    *val = env->vxsat;
 665    return RISCV_EXCP_NONE;
 666}
 667
 668static RISCVException write_vxsat(CPURISCVState *env, int csrno,
 669                                  target_ulong val)
 670{
 671#if !defined(CONFIG_USER_ONLY)
 672    env->mstatus |= MSTATUS_VS;
 673#endif
 674    env->vxsat = val;
 675    return RISCV_EXCP_NONE;
 676}
 677
 678static RISCVException read_vstart(CPURISCVState *env, int csrno,
 679                                  target_ulong *val)
 680{
 681    *val = env->vstart;
 682    return RISCV_EXCP_NONE;
 683}
 684
 685static RISCVException write_vstart(CPURISCVState *env, int csrno,
 686                                   target_ulong val)
 687{
 688#if !defined(CONFIG_USER_ONLY)
 689    env->mstatus |= MSTATUS_VS;
 690#endif
 691    /*
 692     * The vstart CSR is defined to have only enough writable bits
 693     * to hold the largest element index, i.e. lg2(VLEN) bits.
 694     */
 695    env->vstart = val & ~(~0ULL << ctzl(riscv_cpu_cfg(env)->vlen));
 696    return RISCV_EXCP_NONE;
 697}
 698
 699static int read_vcsr(CPURISCVState *env, int csrno, target_ulong *val)
 700{
 701    *val = (env->vxrm << VCSR_VXRM_SHIFT) | (env->vxsat << VCSR_VXSAT_SHIFT);
 702    return RISCV_EXCP_NONE;
 703}
 704
 705static int write_vcsr(CPURISCVState *env, int csrno, target_ulong val)
 706{
 707#if !defined(CONFIG_USER_ONLY)
 708    env->mstatus |= MSTATUS_VS;
 709#endif
 710    env->vxrm = (val & VCSR_VXRM) >> VCSR_VXRM_SHIFT;
 711    env->vxsat = (val & VCSR_VXSAT) >> VCSR_VXSAT_SHIFT;
 712    return RISCV_EXCP_NONE;
 713}
 714
 715/* User Timers and Counters */
 716static target_ulong get_ticks(bool shift)
 717{
 718    int64_t val;
 719    target_ulong result;
 720
 721#if !defined(CONFIG_USER_ONLY)
 722    if (icount_enabled()) {
 723        val = icount_get();
 724    } else {
 725        val = cpu_get_host_ticks();
 726    }
 727#else
 728    val = cpu_get_host_ticks();
 729#endif
 730
 731    if (shift) {
 732        result = val >> 32;
 733    } else {
 734        result = val;
 735    }
 736
 737    return result;
 738}
 739
 740#if defined(CONFIG_USER_ONLY)
 741static RISCVException read_time(CPURISCVState *env, int csrno,
 742                                target_ulong *val)
 743{
 744    *val = cpu_get_host_ticks();
 745    return RISCV_EXCP_NONE;
 746}
 747
 748static RISCVException read_timeh(CPURISCVState *env, int csrno,
 749                                 target_ulong *val)
 750{
 751    *val = cpu_get_host_ticks() >> 32;
 752    return RISCV_EXCP_NONE;
 753}
 754
 755static int read_hpmcounter(CPURISCVState *env, int csrno, target_ulong *val)
 756{
 757    *val = get_ticks(false);
 758    return RISCV_EXCP_NONE;
 759}
 760
 761static int read_hpmcounterh(CPURISCVState *env, int csrno, target_ulong *val)
 762{
 763    *val = get_ticks(true);
 764    return RISCV_EXCP_NONE;
 765}
 766
 767#else /* CONFIG_USER_ONLY */
 768
 769static int read_mhpmevent(CPURISCVState *env, int csrno, target_ulong *val)
 770{
 771    int evt_index = csrno - CSR_MCOUNTINHIBIT;
 772
 773    *val = env->mhpmevent_val[evt_index];
 774
 775    return RISCV_EXCP_NONE;
 776}
 777
 778static int write_mhpmevent(CPURISCVState *env, int csrno, target_ulong val)
 779{
 780    int evt_index = csrno - CSR_MCOUNTINHIBIT;
 781    uint64_t mhpmevt_val = val;
 782
 783    env->mhpmevent_val[evt_index] = val;
 784
 785    if (riscv_cpu_mxl(env) == MXL_RV32) {
 786        mhpmevt_val = mhpmevt_val |
 787                      ((uint64_t)env->mhpmeventh_val[evt_index] << 32);
 788    }
 789    riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
 790
 791    return RISCV_EXCP_NONE;
 792}
 793
 794static int read_mhpmeventh(CPURISCVState *env, int csrno, target_ulong *val)
 795{
 796    int evt_index = csrno - CSR_MHPMEVENT3H + 3;
 797
 798    *val = env->mhpmeventh_val[evt_index];
 799
 800    return RISCV_EXCP_NONE;
 801}
 802
 803static int write_mhpmeventh(CPURISCVState *env, int csrno, target_ulong val)
 804{
 805    int evt_index = csrno - CSR_MHPMEVENT3H + 3;
 806    uint64_t mhpmevth_val = val;
 807    uint64_t mhpmevt_val = env->mhpmevent_val[evt_index];
 808
 809    mhpmevt_val = mhpmevt_val | (mhpmevth_val << 32);
 810    env->mhpmeventh_val[evt_index] = val;
 811
 812    riscv_pmu_update_event_map(env, mhpmevt_val, evt_index);
 813
 814    return RISCV_EXCP_NONE;
 815}
 816
 817static int write_mhpmcounter(CPURISCVState *env, int csrno, target_ulong val)
 818{
 819    int ctr_idx = csrno - CSR_MCYCLE;
 820    PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
 821    uint64_t mhpmctr_val = val;
 822
 823    counter->mhpmcounter_val = val;
 824    if (riscv_pmu_ctr_monitor_cycles(env, ctr_idx) ||
 825        riscv_pmu_ctr_monitor_instructions(env, ctr_idx)) {
 826        counter->mhpmcounter_prev = get_ticks(false);
 827        if (ctr_idx > 2) {
 828            if (riscv_cpu_mxl(env) == MXL_RV32) {
 829                mhpmctr_val = mhpmctr_val |
 830                              ((uint64_t)counter->mhpmcounterh_val << 32);
 831            }
 832            riscv_pmu_setup_timer(env, mhpmctr_val, ctr_idx);
 833        }
 834     } else {
 835        /* Other counters can keep incrementing from the given value */
 836        counter->mhpmcounter_prev = val;
 837    }
 838
 839    return RISCV_EXCP_NONE;
 840}
 841
 842static int write_mhpmcounterh(CPURISCVState *env, int csrno, target_ulong val)
 843{
 844    int ctr_idx = csrno - CSR_MCYCLEH;
 845    PMUCTRState *counter = &env->pmu_ctrs[ctr_idx];
 846    uint64_t mhpmctr_val = counter->mhpmcounter_val;
 847    uint64_t mhpmctrh_val = val;
 848
 849    counter->mhpmcounterh_val = val;
 850    mhpmctr_val = mhpmctr_val | (mhpmctrh_val << 32);
 851    if (riscv_pmu_ctr_monitor_cycles(env, ctr_idx) ||
 852        riscv_pmu_ctr_monitor_instructions(env, ctr_idx)) {
 853        counter->mhpmcounterh_prev = get_ticks(true);
 854        if (ctr_idx > 2) {
 855            riscv_pmu_setup_timer(env, mhpmctr_val, ctr_idx);
 856        }
 857    } else {
 858        counter->mhpmcounterh_prev = val;
 859    }
 860
 861    return RISCV_EXCP_NONE;
 862}
 863
 864static RISCVException riscv_pmu_read_ctr(CPURISCVState *env, target_ulong *val,
 865                                         bool upper_half, uint32_t ctr_idx)
 866{
 867    PMUCTRState counter = env->pmu_ctrs[ctr_idx];
 868    target_ulong ctr_prev = upper_half ? counter.mhpmcounterh_prev :
 869                                         counter.mhpmcounter_prev;
 870    target_ulong ctr_val = upper_half ? counter.mhpmcounterh_val :
 871                                        counter.mhpmcounter_val;
 872
 873    if (get_field(env->mcountinhibit, BIT(ctr_idx))) {
 874        /**
 875         * Counter should not increment if inhibit bit is set. We can't really
 876         * stop the icount counting. Just return the counter value written by
 877         * the supervisor to indicate that counter was not incremented.
 878         */
 879        if (!counter.started) {
 880            *val = ctr_val;
 881            return RISCV_EXCP_NONE;
 882        } else {
 883            /* Mark that the counter has been stopped */
 884            counter.started = false;
 885        }
 886    }
 887
 888    /**
 889     * The kernel computes the perf delta by subtracting the current value from
 890     * the value it initialized previously (ctr_val).
 891     */
 892    if (riscv_pmu_ctr_monitor_cycles(env, ctr_idx) ||
 893        riscv_pmu_ctr_monitor_instructions(env, ctr_idx)) {
 894        *val = get_ticks(upper_half) - ctr_prev + ctr_val;
 895    } else {
 896        *val = ctr_val;
 897    }
 898
 899    return RISCV_EXCP_NONE;
 900}
 901
 902static int read_hpmcounter(CPURISCVState *env, int csrno, target_ulong *val)
 903{
 904    uint16_t ctr_index;
 905
 906    if (csrno >= CSR_MCYCLE && csrno <= CSR_MHPMCOUNTER31) {
 907        ctr_index = csrno - CSR_MCYCLE;
 908    } else if (csrno >= CSR_CYCLE && csrno <= CSR_HPMCOUNTER31) {
 909        ctr_index = csrno - CSR_CYCLE;
 910    } else {
 911        return RISCV_EXCP_ILLEGAL_INST;
 912    }
 913
 914    return riscv_pmu_read_ctr(env, val, false, ctr_index);
 915}
 916
 917static int read_hpmcounterh(CPURISCVState *env, int csrno, target_ulong *val)
 918{
 919    uint16_t ctr_index;
 920
 921    if (csrno >= CSR_MCYCLEH && csrno <= CSR_MHPMCOUNTER31H) {
 922        ctr_index = csrno - CSR_MCYCLEH;
 923    } else if (csrno >= CSR_CYCLEH && csrno <= CSR_HPMCOUNTER31H) {
 924        ctr_index = csrno - CSR_CYCLEH;
 925    } else {
 926        return RISCV_EXCP_ILLEGAL_INST;
 927    }
 928
 929    return riscv_pmu_read_ctr(env, val, true, ctr_index);
 930}
 931
 932static int read_scountovf(CPURISCVState *env, int csrno, target_ulong *val)
 933{
 934    int mhpmevt_start = CSR_MHPMEVENT3 - CSR_MCOUNTINHIBIT;
 935    int i;
 936    *val = 0;
 937    target_ulong *mhpm_evt_val;
 938    uint64_t of_bit_mask;
 939
 940    if (riscv_cpu_mxl(env) == MXL_RV32) {
 941        mhpm_evt_val = env->mhpmeventh_val;
 942        of_bit_mask = MHPMEVENTH_BIT_OF;
 943    } else {
 944        mhpm_evt_val = env->mhpmevent_val;
 945        of_bit_mask = MHPMEVENT_BIT_OF;
 946    }
 947
 948    for (i = mhpmevt_start; i < RV_MAX_MHPMEVENTS; i++) {
 949        if ((get_field(env->mcounteren, BIT(i))) &&
 950            (mhpm_evt_val[i] & of_bit_mask)) {
 951                    *val |= BIT(i);
 952            }
 953    }
 954
 955    return RISCV_EXCP_NONE;
 956}
 957
 958static RISCVException read_time(CPURISCVState *env, int csrno,
 959                                target_ulong *val)
 960{
 961    uint64_t delta = riscv_cpu_virt_enabled(env) ? env->htimedelta : 0;
 962
 963    if (!env->rdtime_fn) {
 964        return RISCV_EXCP_ILLEGAL_INST;
 965    }
 966
 967    *val = env->rdtime_fn(env->rdtime_fn_arg) + delta;
 968    return RISCV_EXCP_NONE;
 969}
 970
 971static RISCVException read_timeh(CPURISCVState *env, int csrno,
 972                                 target_ulong *val)
 973{
 974    uint64_t delta = riscv_cpu_virt_enabled(env) ? env->htimedelta : 0;
 975
 976    if (!env->rdtime_fn) {
 977        return RISCV_EXCP_ILLEGAL_INST;
 978    }
 979
 980    *val = (env->rdtime_fn(env->rdtime_fn_arg) + delta) >> 32;
 981    return RISCV_EXCP_NONE;
 982}
 983
 984static RISCVException read_vstimecmp(CPURISCVState *env, int csrno,
 985                                     target_ulong *val)
 986{
 987    *val = env->vstimecmp;
 988
 989    return RISCV_EXCP_NONE;
 990}
 991
 992static RISCVException read_vstimecmph(CPURISCVState *env, int csrno,
 993                                      target_ulong *val)
 994{
 995    *val = env->vstimecmp >> 32;
 996
 997    return RISCV_EXCP_NONE;
 998}
 999
1000static RISCVException write_vstimecmp(CPURISCVState *env, int csrno,
1001                                      target_ulong val)
1002{
1003    RISCVCPU *cpu = env_archcpu(env);
1004
1005    if (riscv_cpu_mxl(env) == MXL_RV32) {
1006        env->vstimecmp = deposit64(env->vstimecmp, 0, 32, (uint64_t)val);
1007    } else {
1008        env->vstimecmp = val;
1009    }
1010
1011    riscv_timer_write_timecmp(cpu, env->vstimer, env->vstimecmp,
1012                              env->htimedelta, MIP_VSTIP);
1013
1014    return RISCV_EXCP_NONE;
1015}
1016
1017static RISCVException write_vstimecmph(CPURISCVState *env, int csrno,
1018                                       target_ulong val)
1019{
1020    RISCVCPU *cpu = env_archcpu(env);
1021
1022    env->vstimecmp = deposit64(env->vstimecmp, 32, 32, (uint64_t)val);
1023    riscv_timer_write_timecmp(cpu, env->vstimer, env->vstimecmp,
1024                              env->htimedelta, MIP_VSTIP);
1025
1026    return RISCV_EXCP_NONE;
1027}
1028
1029static RISCVException read_stimecmp(CPURISCVState *env, int csrno,
1030                                    target_ulong *val)
1031{
1032    if (riscv_cpu_virt_enabled(env)) {
1033        *val = env->vstimecmp;
1034    } else {
1035        *val = env->stimecmp;
1036    }
1037
1038    return RISCV_EXCP_NONE;
1039}
1040
1041static RISCVException read_stimecmph(CPURISCVState *env, int csrno,
1042                                     target_ulong *val)
1043{
1044    if (riscv_cpu_virt_enabled(env)) {
1045        *val = env->vstimecmp >> 32;
1046    } else {
1047        *val = env->stimecmp >> 32;
1048    }
1049
1050    return RISCV_EXCP_NONE;
1051}
1052
1053static RISCVException write_stimecmp(CPURISCVState *env, int csrno,
1054                                     target_ulong val)
1055{
1056    RISCVCPU *cpu = env_archcpu(env);
1057
1058    if (riscv_cpu_virt_enabled(env)) {
1059        if (env->hvictl & HVICTL_VTI) {
1060            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
1061        }
1062        return write_vstimecmp(env, csrno, val);
1063    }
1064
1065    if (riscv_cpu_mxl(env) == MXL_RV32) {
1066        env->stimecmp = deposit64(env->stimecmp, 0, 32, (uint64_t)val);
1067    } else {
1068        env->stimecmp = val;
1069    }
1070
1071    riscv_timer_write_timecmp(cpu, env->stimer, env->stimecmp, 0, MIP_STIP);
1072
1073    return RISCV_EXCP_NONE;
1074}
1075
1076static RISCVException write_stimecmph(CPURISCVState *env, int csrno,
1077                                      target_ulong val)
1078{
1079    RISCVCPU *cpu = env_archcpu(env);
1080
1081    if (riscv_cpu_virt_enabled(env)) {
1082        if (env->hvictl & HVICTL_VTI) {
1083            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
1084        }
1085        return write_vstimecmph(env, csrno, val);
1086    }
1087
1088    env->stimecmp = deposit64(env->stimecmp, 32, 32, (uint64_t)val);
1089    riscv_timer_write_timecmp(cpu, env->stimer, env->stimecmp, 0, MIP_STIP);
1090
1091    return RISCV_EXCP_NONE;
1092}
1093
1094/* Machine constants */
1095
1096#define M_MODE_INTERRUPTS  ((uint64_t)(MIP_MSIP | MIP_MTIP | MIP_MEIP))
1097#define S_MODE_INTERRUPTS  ((uint64_t)(MIP_SSIP | MIP_STIP | MIP_SEIP | \
1098                                      MIP_LCOFIP))
1099#define VS_MODE_INTERRUPTS ((uint64_t)(MIP_VSSIP | MIP_VSTIP | MIP_VSEIP))
1100#define HS_MODE_INTERRUPTS ((uint64_t)(MIP_SGEIP | VS_MODE_INTERRUPTS))
1101
1102#define VSTOPI_NUM_SRCS 5
1103
1104static const uint64_t delegable_ints = S_MODE_INTERRUPTS |
1105                                           VS_MODE_INTERRUPTS;
1106static const uint64_t vs_delegable_ints = VS_MODE_INTERRUPTS;
1107static const uint64_t all_ints = M_MODE_INTERRUPTS | S_MODE_INTERRUPTS |
1108                                     HS_MODE_INTERRUPTS;
1109#define DELEGABLE_EXCPS ((1ULL << (RISCV_EXCP_INST_ADDR_MIS)) | \
1110                         (1ULL << (RISCV_EXCP_INST_ACCESS_FAULT)) | \
1111                         (1ULL << (RISCV_EXCP_ILLEGAL_INST)) | \
1112                         (1ULL << (RISCV_EXCP_BREAKPOINT)) | \
1113                         (1ULL << (RISCV_EXCP_LOAD_ADDR_MIS)) | \
1114                         (1ULL << (RISCV_EXCP_LOAD_ACCESS_FAULT)) | \
1115                         (1ULL << (RISCV_EXCP_STORE_AMO_ADDR_MIS)) | \
1116                         (1ULL << (RISCV_EXCP_STORE_AMO_ACCESS_FAULT)) | \
1117                         (1ULL << (RISCV_EXCP_U_ECALL)) | \
1118                         (1ULL << (RISCV_EXCP_S_ECALL)) | \
1119                         (1ULL << (RISCV_EXCP_VS_ECALL)) | \
1120                         (1ULL << (RISCV_EXCP_M_ECALL)) | \
1121                         (1ULL << (RISCV_EXCP_INST_PAGE_FAULT)) | \
1122                         (1ULL << (RISCV_EXCP_LOAD_PAGE_FAULT)) | \
1123                         (1ULL << (RISCV_EXCP_STORE_PAGE_FAULT)) | \
1124                         (1ULL << (RISCV_EXCP_INST_GUEST_PAGE_FAULT)) | \
1125                         (1ULL << (RISCV_EXCP_LOAD_GUEST_ACCESS_FAULT)) | \
1126                         (1ULL << (RISCV_EXCP_VIRT_INSTRUCTION_FAULT)) | \
1127                         (1ULL << (RISCV_EXCP_STORE_GUEST_AMO_ACCESS_FAULT)))
1128static const target_ulong vs_delegable_excps = DELEGABLE_EXCPS &
1129    ~((1ULL << (RISCV_EXCP_S_ECALL)) |
1130      (1ULL << (RISCV_EXCP_VS_ECALL)) |
1131      (1ULL << (RISCV_EXCP_M_ECALL)) |
1132      (1ULL << (RISCV_EXCP_INST_GUEST_PAGE_FAULT)) |
1133      (1ULL << (RISCV_EXCP_LOAD_GUEST_ACCESS_FAULT)) |
1134      (1ULL << (RISCV_EXCP_VIRT_INSTRUCTION_FAULT)) |
1135      (1ULL << (RISCV_EXCP_STORE_GUEST_AMO_ACCESS_FAULT)));
1136static const target_ulong sstatus_v1_10_mask = SSTATUS_SIE | SSTATUS_SPIE |
1137    SSTATUS_UIE | SSTATUS_UPIE | SSTATUS_SPP | SSTATUS_FS | SSTATUS_XS |
1138    SSTATUS_SUM | SSTATUS_MXR | SSTATUS_VS;
1139static const target_ulong sip_writable_mask = SIP_SSIP | MIP_USIP | MIP_UEIP |
1140                                              SIP_LCOFIP;
1141static const target_ulong hip_writable_mask = MIP_VSSIP;
1142static const target_ulong hvip_writable_mask = MIP_VSSIP | MIP_VSTIP | MIP_VSEIP;
1143static const target_ulong vsip_writable_mask = MIP_VSSIP;
1144
1145const bool valid_vm_1_10_32[16] = {
1146    [VM_1_10_MBARE] = true,
1147    [VM_1_10_SV32] = true
1148};
1149
1150const bool valid_vm_1_10_64[16] = {
1151    [VM_1_10_MBARE] = true,
1152    [VM_1_10_SV39] = true,
1153    [VM_1_10_SV48] = true,
1154    [VM_1_10_SV57] = true
1155};
1156
1157/* Machine Information Registers */
1158static RISCVException read_zero(CPURISCVState *env, int csrno,
1159                                target_ulong *val)
1160{
1161    *val = 0;
1162    return RISCV_EXCP_NONE;
1163}
1164
1165static RISCVException write_ignore(CPURISCVState *env, int csrno,
1166                                   target_ulong val)
1167{
1168    return RISCV_EXCP_NONE;
1169}
1170
1171static RISCVException read_mvendorid(CPURISCVState *env, int csrno,
1172                                     target_ulong *val)
1173{
1174    RISCVCPU *cpu = env_archcpu(env);
1175
1176    *val = cpu->cfg.mvendorid;
1177    return RISCV_EXCP_NONE;
1178}
1179
1180static RISCVException read_marchid(CPURISCVState *env, int csrno,
1181                                   target_ulong *val)
1182{
1183    RISCVCPU *cpu = env_archcpu(env);
1184
1185    *val = cpu->cfg.marchid;
1186    return RISCV_EXCP_NONE;
1187}
1188
1189static RISCVException read_mimpid(CPURISCVState *env, int csrno,
1190                                  target_ulong *val)
1191{
1192    RISCVCPU *cpu = env_archcpu(env);
1193
1194    *val = cpu->cfg.mimpid;
1195    return RISCV_EXCP_NONE;
1196}
1197
1198static RISCVException read_mhartid(CPURISCVState *env, int csrno,
1199                                   target_ulong *val)
1200{
1201    *val = env->mhartid;
1202    return RISCV_EXCP_NONE;
1203}
1204
1205/* Machine Trap Setup */
1206
1207/* We do not store SD explicitly, only compute it on demand. */
1208static uint64_t add_status_sd(RISCVMXL xl, uint64_t status)
1209{
1210    if ((status & MSTATUS_FS) == MSTATUS_FS ||
1211        (status & MSTATUS_VS) == MSTATUS_VS ||
1212        (status & MSTATUS_XS) == MSTATUS_XS) {
1213        switch (xl) {
1214        case MXL_RV32:
1215            return status | MSTATUS32_SD;
1216        case MXL_RV64:
1217            return status | MSTATUS64_SD;
1218        case MXL_RV128:
1219            return MSTATUSH128_SD;
1220        default:
1221            g_assert_not_reached();
1222        }
1223    }
1224    return status;
1225}
1226
1227static RISCVException read_mstatus(CPURISCVState *env, int csrno,
1228                                   target_ulong *val)
1229{
1230    *val = add_status_sd(riscv_cpu_mxl(env), env->mstatus);
1231    return RISCV_EXCP_NONE;
1232}
1233
1234static bool validate_vm(CPURISCVState *env, target_ulong vm)
1235{
1236    RISCVCPU *cpu = RISCV_CPU(env_cpu(env));
1237
1238    return (vm & 0xf) <= satp_mode_max_from_map(cpu->cfg.satp_mode.map);
1239}
1240
1241static RISCVException write_mstatus(CPURISCVState *env, int csrno,
1242                                    target_ulong val)
1243{
1244    uint64_t mstatus = env->mstatus;
1245    uint64_t mask = 0;
1246    RISCVMXL xl = riscv_cpu_mxl(env);
1247
1248    /* flush tlb on mstatus fields that affect VM */
1249    if ((val ^ mstatus) & (MSTATUS_MXR | MSTATUS_MPP | MSTATUS_MPV |
1250            MSTATUS_MPRV | MSTATUS_SUM)) {
1251        tlb_flush(env_cpu(env));
1252    }
1253    mask = MSTATUS_SIE | MSTATUS_SPIE | MSTATUS_MIE | MSTATUS_MPIE |
1254        MSTATUS_SPP | MSTATUS_MPRV | MSTATUS_SUM |
1255        MSTATUS_MPP | MSTATUS_MXR | MSTATUS_TVM | MSTATUS_TSR |
1256        MSTATUS_TW | MSTATUS_VS;
1257
1258    if (riscv_has_ext(env, RVF)) {
1259        mask |= MSTATUS_FS;
1260    }
1261
1262    if (xl != MXL_RV32 || env->debugger) {
1263        /*
1264         * RV32: MPV and GVA are not in mstatus. The current plan is to
1265         * add them to mstatush. For now, we just don't support it.
1266         */
1267        mask |= MSTATUS_MPV | MSTATUS_GVA;
1268        if ((val & MSTATUS64_UXL) != 0) {
1269            mask |= MSTATUS64_UXL;
1270        }
1271    }
1272
1273    mstatus = (mstatus & ~mask) | (val & mask);
1274
1275    if (xl > MXL_RV32) {
1276        /* SXL field is for now read only */
1277        mstatus = set_field(mstatus, MSTATUS64_SXL, xl);
1278    }
1279    env->mstatus = mstatus;
1280    env->xl = cpu_recompute_xl(env);
1281
1282    return RISCV_EXCP_NONE;
1283}
1284
1285static RISCVException read_mstatush(CPURISCVState *env, int csrno,
1286                                    target_ulong *val)
1287{
1288    *val = env->mstatus >> 32;
1289    return RISCV_EXCP_NONE;
1290}
1291
1292static RISCVException write_mstatush(CPURISCVState *env, int csrno,
1293                                     target_ulong val)
1294{
1295    uint64_t valh = (uint64_t)val << 32;
1296    uint64_t mask = MSTATUS_MPV | MSTATUS_GVA;
1297
1298    if ((valh ^ env->mstatus) & (MSTATUS_MPV)) {
1299        tlb_flush(env_cpu(env));
1300    }
1301
1302    env->mstatus = (env->mstatus & ~mask) | (valh & mask);
1303
1304    return RISCV_EXCP_NONE;
1305}
1306
1307static RISCVException read_mstatus_i128(CPURISCVState *env, int csrno,
1308                                        Int128 *val)
1309{
1310    *val = int128_make128(env->mstatus, add_status_sd(MXL_RV128, env->mstatus));
1311    return RISCV_EXCP_NONE;
1312}
1313
1314static RISCVException read_misa_i128(CPURISCVState *env, int csrno,
1315                                     Int128 *val)
1316{
1317    *val = int128_make128(env->misa_ext, (uint64_t)MXL_RV128 << 62);
1318    return RISCV_EXCP_NONE;
1319}
1320
1321static RISCVException read_misa(CPURISCVState *env, int csrno,
1322                                target_ulong *val)
1323{
1324    target_ulong misa;
1325
1326    switch (env->misa_mxl) {
1327    case MXL_RV32:
1328        misa = (target_ulong)MXL_RV32 << 30;
1329        break;
1330#ifdef TARGET_RISCV64
1331    case MXL_RV64:
1332        misa = (target_ulong)MXL_RV64 << 62;
1333        break;
1334#endif
1335    default:
1336        g_assert_not_reached();
1337    }
1338
1339    *val = misa | env->misa_ext;
1340    return RISCV_EXCP_NONE;
1341}
1342
1343static RISCVException write_misa(CPURISCVState *env, int csrno,
1344                                 target_ulong val)
1345{
1346    if (!riscv_cpu_cfg(env)->misa_w) {
1347        /* drop write to misa */
1348        return RISCV_EXCP_NONE;
1349    }
1350
1351    /* 'I' or 'E' must be present */
1352    if (!(val & (RVI | RVE))) {
1353        /* It is not, drop write to misa */
1354        return RISCV_EXCP_NONE;
1355    }
1356
1357    /* 'E' excludes all other extensions */
1358    if (val & RVE) {
1359        /*
1360         * when we support 'E' we can do "val = RVE;" however
1361         * for now we just drop writes if 'E' is present.
1362         */
1363        return RISCV_EXCP_NONE;
1364    }
1365
1366    /*
1367     * misa.MXL writes are not supported by QEMU.
1368     * Drop writes to those bits.
1369     */
1370
1371    /* Mask extensions that are not supported by this hart */
1372    val &= env->misa_ext_mask;
1373
1374    /* 'D' depends on 'F', so clear 'D' if 'F' is not present */
1375    if ((val & RVD) && !(val & RVF)) {
1376        val &= ~RVD;
1377    }
1378
1379    /*
1380     * Suppress 'C' if next instruction is not aligned
1381     * TODO: this should check next_pc
1382     */
1383    if ((val & RVC) && (GETPC() & ~3) != 0) {
1384        val &= ~RVC;
1385    }
1386
1387    /* If nothing changed, do nothing. */
1388    if (val == env->misa_ext) {
1389        return RISCV_EXCP_NONE;
1390    }
1391
1392    if (!(val & RVF)) {
1393        env->mstatus &= ~MSTATUS_FS;
1394    }
1395
1396    /* flush translation cache */
1397    tb_flush(env_cpu(env));
1398    env->misa_ext = val;
1399    env->xl = riscv_cpu_mxl(env);
1400    return RISCV_EXCP_NONE;
1401}
1402
1403static RISCVException read_medeleg(CPURISCVState *env, int csrno,
1404                                   target_ulong *val)
1405{
1406    *val = env->medeleg;
1407    return RISCV_EXCP_NONE;
1408}
1409
1410static RISCVException write_medeleg(CPURISCVState *env, int csrno,
1411                                    target_ulong val)
1412{
1413    env->medeleg = (env->medeleg & ~DELEGABLE_EXCPS) | (val & DELEGABLE_EXCPS);
1414    return RISCV_EXCP_NONE;
1415}
1416
1417static RISCVException rmw_mideleg64(CPURISCVState *env, int csrno,
1418                                    uint64_t *ret_val,
1419                                    uint64_t new_val, uint64_t wr_mask)
1420{
1421    uint64_t mask = wr_mask & delegable_ints;
1422
1423    if (ret_val) {
1424        *ret_val = env->mideleg;
1425    }
1426
1427    env->mideleg = (env->mideleg & ~mask) | (new_val & mask);
1428
1429    if (riscv_has_ext(env, RVH)) {
1430        env->mideleg |= HS_MODE_INTERRUPTS;
1431    }
1432
1433    return RISCV_EXCP_NONE;
1434}
1435
1436static RISCVException rmw_mideleg(CPURISCVState *env, int csrno,
1437                                  target_ulong *ret_val,
1438                                  target_ulong new_val, target_ulong wr_mask)
1439{
1440    uint64_t rval;
1441    RISCVException ret;
1442
1443    ret = rmw_mideleg64(env, csrno, &rval, new_val, wr_mask);
1444    if (ret_val) {
1445        *ret_val = rval;
1446    }
1447
1448    return ret;
1449}
1450
1451static RISCVException rmw_midelegh(CPURISCVState *env, int csrno,
1452                                   target_ulong *ret_val,
1453                                   target_ulong new_val,
1454                                   target_ulong wr_mask)
1455{
1456    uint64_t rval;
1457    RISCVException ret;
1458
1459    ret = rmw_mideleg64(env, csrno, &rval,
1460        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
1461    if (ret_val) {
1462        *ret_val = rval >> 32;
1463    }
1464
1465    return ret;
1466}
1467
1468static RISCVException rmw_mie64(CPURISCVState *env, int csrno,
1469                                uint64_t *ret_val,
1470                                uint64_t new_val, uint64_t wr_mask)
1471{
1472    uint64_t mask = wr_mask & all_ints;
1473
1474    if (ret_val) {
1475        *ret_val = env->mie;
1476    }
1477
1478    env->mie = (env->mie & ~mask) | (new_val & mask);
1479
1480    if (!riscv_has_ext(env, RVH)) {
1481        env->mie &= ~((uint64_t)MIP_SGEIP);
1482    }
1483
1484    return RISCV_EXCP_NONE;
1485}
1486
1487static RISCVException rmw_mie(CPURISCVState *env, int csrno,
1488                              target_ulong *ret_val,
1489                              target_ulong new_val, target_ulong wr_mask)
1490{
1491    uint64_t rval;
1492    RISCVException ret;
1493
1494    ret = rmw_mie64(env, csrno, &rval, new_val, wr_mask);
1495    if (ret_val) {
1496        *ret_val = rval;
1497    }
1498
1499    return ret;
1500}
1501
1502static RISCVException rmw_mieh(CPURISCVState *env, int csrno,
1503                               target_ulong *ret_val,
1504                               target_ulong new_val, target_ulong wr_mask)
1505{
1506    uint64_t rval;
1507    RISCVException ret;
1508
1509    ret = rmw_mie64(env, csrno, &rval,
1510        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
1511    if (ret_val) {
1512        *ret_val = rval >> 32;
1513    }
1514
1515    return ret;
1516}
1517
1518static int read_mtopi(CPURISCVState *env, int csrno, target_ulong *val)
1519{
1520    int irq;
1521    uint8_t iprio;
1522
1523    irq = riscv_cpu_mirq_pending(env);
1524    if (irq <= 0 || irq > 63) {
1525        *val = 0;
1526    } else {
1527        iprio = env->miprio[irq];
1528        if (!iprio) {
1529            if (riscv_cpu_default_priority(irq) > IPRIO_DEFAULT_M) {
1530                iprio = IPRIO_MMAXIPRIO;
1531            }
1532        }
1533        *val = (irq & TOPI_IID_MASK) << TOPI_IID_SHIFT;
1534        *val |= iprio;
1535    }
1536
1537    return RISCV_EXCP_NONE;
1538}
1539
1540static int aia_xlate_vs_csrno(CPURISCVState *env, int csrno)
1541{
1542    if (!riscv_cpu_virt_enabled(env)) {
1543        return csrno;
1544    }
1545
1546    switch (csrno) {
1547    case CSR_SISELECT:
1548        return CSR_VSISELECT;
1549    case CSR_SIREG:
1550        return CSR_VSIREG;
1551    case CSR_STOPEI:
1552        return CSR_VSTOPEI;
1553    default:
1554        return csrno;
1555    };
1556}
1557
1558static int rmw_xiselect(CPURISCVState *env, int csrno, target_ulong *val,
1559                        target_ulong new_val, target_ulong wr_mask)
1560{
1561    target_ulong *iselect;
1562
1563    /* Translate CSR number for VS-mode */
1564    csrno = aia_xlate_vs_csrno(env, csrno);
1565
1566    /* Find the iselect CSR based on CSR number */
1567    switch (csrno) {
1568    case CSR_MISELECT:
1569        iselect = &env->miselect;
1570        break;
1571    case CSR_SISELECT:
1572        iselect = &env->siselect;
1573        break;
1574    case CSR_VSISELECT:
1575        iselect = &env->vsiselect;
1576        break;
1577    default:
1578         return RISCV_EXCP_ILLEGAL_INST;
1579    };
1580
1581    if (val) {
1582        *val = *iselect;
1583    }
1584
1585    wr_mask &= ISELECT_MASK;
1586    if (wr_mask) {
1587        *iselect = (*iselect & ~wr_mask) | (new_val & wr_mask);
1588    }
1589
1590    return RISCV_EXCP_NONE;
1591}
1592
1593static int rmw_iprio(target_ulong xlen,
1594                     target_ulong iselect, uint8_t *iprio,
1595                     target_ulong *val, target_ulong new_val,
1596                     target_ulong wr_mask, int ext_irq_no)
1597{
1598    int i, firq, nirqs;
1599    target_ulong old_val;
1600
1601    if (iselect < ISELECT_IPRIO0 || ISELECT_IPRIO15 < iselect) {
1602        return -EINVAL;
1603    }
1604    if (xlen != 32 && iselect & 0x1) {
1605        return -EINVAL;
1606    }
1607
1608    nirqs = 4 * (xlen / 32);
1609    firq = ((iselect - ISELECT_IPRIO0) / (xlen / 32)) * (nirqs);
1610
1611    old_val = 0;
1612    for (i = 0; i < nirqs; i++) {
1613        old_val |= ((target_ulong)iprio[firq + i]) << (IPRIO_IRQ_BITS * i);
1614    }
1615
1616    if (val) {
1617        *val = old_val;
1618    }
1619
1620    if (wr_mask) {
1621        new_val = (old_val & ~wr_mask) | (new_val & wr_mask);
1622        for (i = 0; i < nirqs; i++) {
1623            /*
1624             * M-level and S-level external IRQ priority always read-only
1625             * zero. This means default priority order is always preferred
1626             * for M-level and S-level external IRQs.
1627             */
1628            if ((firq + i) == ext_irq_no) {
1629                continue;
1630            }
1631            iprio[firq + i] = (new_val >> (IPRIO_IRQ_BITS * i)) & 0xff;
1632        }
1633    }
1634
1635    return 0;
1636}
1637
1638static int rmw_xireg(CPURISCVState *env, int csrno, target_ulong *val,
1639                     target_ulong new_val, target_ulong wr_mask)
1640{
1641    bool virt;
1642    uint8_t *iprio;
1643    int ret = -EINVAL;
1644    target_ulong priv, isel, vgein;
1645
1646    /* Translate CSR number for VS-mode */
1647    csrno = aia_xlate_vs_csrno(env, csrno);
1648
1649    /* Decode register details from CSR number */
1650    virt = false;
1651    switch (csrno) {
1652    case CSR_MIREG:
1653        iprio = env->miprio;
1654        isel = env->miselect;
1655        priv = PRV_M;
1656        break;
1657    case CSR_SIREG:
1658        iprio = env->siprio;
1659        isel = env->siselect;
1660        priv = PRV_S;
1661        break;
1662    case CSR_VSIREG:
1663        iprio = env->hviprio;
1664        isel = env->vsiselect;
1665        priv = PRV_S;
1666        virt = true;
1667        break;
1668    default:
1669         goto done;
1670    };
1671
1672    /* Find the selected guest interrupt file */
1673    vgein = (virt) ? get_field(env->hstatus, HSTATUS_VGEIN) : 0;
1674
1675    if (ISELECT_IPRIO0 <= isel && isel <= ISELECT_IPRIO15) {
1676        /* Local interrupt priority registers not available for VS-mode */
1677        if (!virt) {
1678            ret = rmw_iprio(riscv_cpu_mxl_bits(env),
1679                            isel, iprio, val, new_val, wr_mask,
1680                            (priv == PRV_M) ? IRQ_M_EXT : IRQ_S_EXT);
1681        }
1682    } else if (ISELECT_IMSIC_FIRST <= isel && isel <= ISELECT_IMSIC_LAST) {
1683        /* IMSIC registers only available when machine implements it. */
1684        if (env->aia_ireg_rmw_fn[priv]) {
1685            /* Selected guest interrupt file should not be zero */
1686            if (virt && (!vgein || env->geilen < vgein)) {
1687                goto done;
1688            }
1689            /* Call machine specific IMSIC register emulation */
1690            ret = env->aia_ireg_rmw_fn[priv](env->aia_ireg_rmw_fn_arg[priv],
1691                                    AIA_MAKE_IREG(isel, priv, virt, vgein,
1692                                                  riscv_cpu_mxl_bits(env)),
1693                                    val, new_val, wr_mask);
1694        }
1695    }
1696
1697done:
1698    if (ret) {
1699        return (riscv_cpu_virt_enabled(env) && virt) ?
1700               RISCV_EXCP_VIRT_INSTRUCTION_FAULT : RISCV_EXCP_ILLEGAL_INST;
1701    }
1702    return RISCV_EXCP_NONE;
1703}
1704
1705static int rmw_xtopei(CPURISCVState *env, int csrno, target_ulong *val,
1706                      target_ulong new_val, target_ulong wr_mask)
1707{
1708    bool virt;
1709    int ret = -EINVAL;
1710    target_ulong priv, vgein;
1711
1712    /* Translate CSR number for VS-mode */
1713    csrno = aia_xlate_vs_csrno(env, csrno);
1714
1715    /* Decode register details from CSR number */
1716    virt = false;
1717    switch (csrno) {
1718    case CSR_MTOPEI:
1719        priv = PRV_M;
1720        break;
1721    case CSR_STOPEI:
1722        priv = PRV_S;
1723        break;
1724    case CSR_VSTOPEI:
1725        priv = PRV_S;
1726        virt = true;
1727        break;
1728    default:
1729        goto done;
1730    };
1731
1732    /* IMSIC CSRs only available when machine implements IMSIC. */
1733    if (!env->aia_ireg_rmw_fn[priv]) {
1734        goto done;
1735    }
1736
1737    /* Find the selected guest interrupt file */
1738    vgein = (virt) ? get_field(env->hstatus, HSTATUS_VGEIN) : 0;
1739
1740    /* Selected guest interrupt file should be valid */
1741    if (virt && (!vgein || env->geilen < vgein)) {
1742        goto done;
1743    }
1744
1745    /* Call machine specific IMSIC register emulation for TOPEI */
1746    ret = env->aia_ireg_rmw_fn[priv](env->aia_ireg_rmw_fn_arg[priv],
1747                    AIA_MAKE_IREG(ISELECT_IMSIC_TOPEI, priv, virt, vgein,
1748                                  riscv_cpu_mxl_bits(env)),
1749                    val, new_val, wr_mask);
1750
1751done:
1752    if (ret) {
1753        return (riscv_cpu_virt_enabled(env) && virt) ?
1754               RISCV_EXCP_VIRT_INSTRUCTION_FAULT : RISCV_EXCP_ILLEGAL_INST;
1755    }
1756    return RISCV_EXCP_NONE;
1757}
1758
1759static RISCVException read_mtvec(CPURISCVState *env, int csrno,
1760                                 target_ulong *val)
1761{
1762    *val = env->mtvec;
1763    return RISCV_EXCP_NONE;
1764}
1765
1766static RISCVException write_mtvec(CPURISCVState *env, int csrno,
1767                                  target_ulong val)
1768{
1769    /* bits [1:0] encode mode; 0 = direct, 1 = vectored, 2 >= reserved */
1770    if ((val & 3) < 2) {
1771        env->mtvec = val;
1772    } else {
1773        qemu_log_mask(LOG_UNIMP, "CSR_MTVEC: reserved mode not supported\n");
1774    }
1775    return RISCV_EXCP_NONE;
1776}
1777
1778static RISCVException read_mcountinhibit(CPURISCVState *env, int csrno,
1779                                         target_ulong *val)
1780{
1781    *val = env->mcountinhibit;
1782    return RISCV_EXCP_NONE;
1783}
1784
1785static RISCVException write_mcountinhibit(CPURISCVState *env, int csrno,
1786                                          target_ulong val)
1787{
1788    int cidx;
1789    PMUCTRState *counter;
1790
1791    env->mcountinhibit = val;
1792
1793    /* Check if any other counter is also monitoring cycles/instructions */
1794    for (cidx = 0; cidx < RV_MAX_MHPMCOUNTERS; cidx++) {
1795        if (!get_field(env->mcountinhibit, BIT(cidx))) {
1796            counter = &env->pmu_ctrs[cidx];
1797            counter->started = true;
1798        }
1799    }
1800
1801    return RISCV_EXCP_NONE;
1802}
1803
1804static RISCVException read_mcounteren(CPURISCVState *env, int csrno,
1805                                      target_ulong *val)
1806{
1807    *val = env->mcounteren;
1808    return RISCV_EXCP_NONE;
1809}
1810
1811static RISCVException write_mcounteren(CPURISCVState *env, int csrno,
1812                                       target_ulong val)
1813{
1814    env->mcounteren = val;
1815    return RISCV_EXCP_NONE;
1816}
1817
1818/* Machine Trap Handling */
1819static RISCVException read_mscratch_i128(CPURISCVState *env, int csrno,
1820                                         Int128 *val)
1821{
1822    *val = int128_make128(env->mscratch, env->mscratchh);
1823    return RISCV_EXCP_NONE;
1824}
1825
1826static RISCVException write_mscratch_i128(CPURISCVState *env, int csrno,
1827                                          Int128 val)
1828{
1829    env->mscratch = int128_getlo(val);
1830    env->mscratchh = int128_gethi(val);
1831    return RISCV_EXCP_NONE;
1832}
1833
1834static RISCVException read_mscratch(CPURISCVState *env, int csrno,
1835                                    target_ulong *val)
1836{
1837    *val = env->mscratch;
1838    return RISCV_EXCP_NONE;
1839}
1840
1841static RISCVException write_mscratch(CPURISCVState *env, int csrno,
1842                                     target_ulong val)
1843{
1844    env->mscratch = val;
1845    return RISCV_EXCP_NONE;
1846}
1847
1848static RISCVException read_mepc(CPURISCVState *env, int csrno,
1849                                target_ulong *val)
1850{
1851    *val = env->mepc;
1852    return RISCV_EXCP_NONE;
1853}
1854
1855static RISCVException write_mepc(CPURISCVState *env, int csrno,
1856                                 target_ulong val)
1857{
1858    env->mepc = val;
1859    return RISCV_EXCP_NONE;
1860}
1861
1862static RISCVException read_mcause(CPURISCVState *env, int csrno,
1863                                  target_ulong *val)
1864{
1865    *val = env->mcause;
1866    return RISCV_EXCP_NONE;
1867}
1868
1869static RISCVException write_mcause(CPURISCVState *env, int csrno,
1870                                   target_ulong val)
1871{
1872    env->mcause = val;
1873    return RISCV_EXCP_NONE;
1874}
1875
1876static RISCVException read_mtval(CPURISCVState *env, int csrno,
1877                                 target_ulong *val)
1878{
1879    *val = env->mtval;
1880    return RISCV_EXCP_NONE;
1881}
1882
1883static RISCVException write_mtval(CPURISCVState *env, int csrno,
1884                                  target_ulong val)
1885{
1886    env->mtval = val;
1887    return RISCV_EXCP_NONE;
1888}
1889
1890/* Execution environment configuration setup */
1891static RISCVException read_menvcfg(CPURISCVState *env, int csrno,
1892                                   target_ulong *val)
1893{
1894    *val = env->menvcfg;
1895    return RISCV_EXCP_NONE;
1896}
1897
1898static RISCVException write_menvcfg(CPURISCVState *env, int csrno,
1899                                    target_ulong val)
1900{
1901    RISCVCPUConfig *cfg = &env_archcpu(env)->cfg;
1902    uint64_t mask = MENVCFG_FIOM | MENVCFG_CBIE | MENVCFG_CBCFE | MENVCFG_CBZE;
1903
1904    if (riscv_cpu_mxl(env) == MXL_RV64) {
1905        mask |= (cfg->ext_svpbmt ? MENVCFG_PBMTE : 0) |
1906                (cfg->ext_sstc ? MENVCFG_STCE : 0) |
1907                (cfg->ext_svadu ? MENVCFG_HADE : 0);
1908    }
1909    env->menvcfg = (env->menvcfg & ~mask) | (val & mask);
1910
1911    return RISCV_EXCP_NONE;
1912}
1913
1914static RISCVException read_menvcfgh(CPURISCVState *env, int csrno,
1915                                    target_ulong *val)
1916{
1917    *val = env->menvcfg >> 32;
1918    return RISCV_EXCP_NONE;
1919}
1920
1921static RISCVException write_menvcfgh(CPURISCVState *env, int csrno,
1922                                     target_ulong val)
1923{
1924    RISCVCPUConfig *cfg = &env_archcpu(env)->cfg;
1925    uint64_t mask = (cfg->ext_svpbmt ? MENVCFG_PBMTE : 0) |
1926                    (cfg->ext_sstc ? MENVCFG_STCE : 0) |
1927                    (cfg->ext_svadu ? MENVCFG_HADE : 0);
1928    uint64_t valh = (uint64_t)val << 32;
1929
1930    env->menvcfg = (env->menvcfg & ~mask) | (valh & mask);
1931
1932    return RISCV_EXCP_NONE;
1933}
1934
1935static RISCVException read_senvcfg(CPURISCVState *env, int csrno,
1936                                   target_ulong *val)
1937{
1938    RISCVException ret;
1939
1940    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
1941    if (ret != RISCV_EXCP_NONE) {
1942        return ret;
1943    }
1944
1945    *val = env->senvcfg;
1946    return RISCV_EXCP_NONE;
1947}
1948
1949static RISCVException write_senvcfg(CPURISCVState *env, int csrno,
1950                                    target_ulong val)
1951{
1952    uint64_t mask = SENVCFG_FIOM | SENVCFG_CBIE | SENVCFG_CBCFE | SENVCFG_CBZE;
1953    RISCVException ret;
1954
1955    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
1956    if (ret != RISCV_EXCP_NONE) {
1957        return ret;
1958    }
1959
1960    env->senvcfg = (env->senvcfg & ~mask) | (val & mask);
1961    return RISCV_EXCP_NONE;
1962}
1963
1964static RISCVException read_henvcfg(CPURISCVState *env, int csrno,
1965                                   target_ulong *val)
1966{
1967    RISCVException ret;
1968
1969    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
1970    if (ret != RISCV_EXCP_NONE) {
1971        return ret;
1972    }
1973
1974    /*
1975     * henvcfg.pbmte is read_only 0 when menvcfg.pbmte = 0
1976     * henvcfg.stce is read_only 0 when menvcfg.stce = 0
1977     * henvcfg.hade is read_only 0 when menvcfg.hade = 0
1978     */
1979    *val = env->henvcfg & (~(HENVCFG_PBMTE | HENVCFG_STCE | HENVCFG_HADE) |
1980                           env->menvcfg);
1981    return RISCV_EXCP_NONE;
1982}
1983
1984static RISCVException write_henvcfg(CPURISCVState *env, int csrno,
1985                                    target_ulong val)
1986{
1987    uint64_t mask = HENVCFG_FIOM | HENVCFG_CBIE | HENVCFG_CBCFE | HENVCFG_CBZE;
1988    RISCVException ret;
1989
1990    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
1991    if (ret != RISCV_EXCP_NONE) {
1992        return ret;
1993    }
1994
1995    if (riscv_cpu_mxl(env) == MXL_RV64) {
1996        mask |= env->menvcfg & (HENVCFG_PBMTE | HENVCFG_STCE | HENVCFG_HADE);
1997    }
1998
1999    env->henvcfg = (env->henvcfg & ~mask) | (val & mask);
2000
2001    return RISCV_EXCP_NONE;
2002}
2003
2004static RISCVException read_henvcfgh(CPURISCVState *env, int csrno,
2005                                    target_ulong *val)
2006{
2007    RISCVException ret;
2008
2009    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
2010    if (ret != RISCV_EXCP_NONE) {
2011        return ret;
2012    }
2013
2014    *val = (env->henvcfg & (~(HENVCFG_PBMTE | HENVCFG_STCE | HENVCFG_HADE) |
2015                            env->menvcfg)) >> 32;
2016    return RISCV_EXCP_NONE;
2017}
2018
2019static RISCVException write_henvcfgh(CPURISCVState *env, int csrno,
2020                                     target_ulong val)
2021{
2022    uint64_t mask = env->menvcfg & (HENVCFG_PBMTE | HENVCFG_STCE |
2023                                    HENVCFG_HADE);
2024    uint64_t valh = (uint64_t)val << 32;
2025    RISCVException ret;
2026
2027    ret = smstateen_acc_ok(env, 0, SMSTATEEN0_HSENVCFG);
2028    if (ret != RISCV_EXCP_NONE) {
2029        return ret;
2030    }
2031
2032    env->henvcfg = (env->henvcfg & ~mask) | (valh & mask);
2033    return RISCV_EXCP_NONE;
2034}
2035
2036static RISCVException read_mstateen(CPURISCVState *env, int csrno,
2037                                    target_ulong *val)
2038{
2039    *val = env->mstateen[csrno - CSR_MSTATEEN0];
2040
2041    return RISCV_EXCP_NONE;
2042}
2043
2044static RISCVException write_mstateen(CPURISCVState *env, int csrno,
2045                                     uint64_t wr_mask, target_ulong new_val)
2046{
2047    uint64_t *reg;
2048
2049    reg = &env->mstateen[csrno - CSR_MSTATEEN0];
2050    *reg = (*reg & ~wr_mask) | (new_val & wr_mask);
2051
2052    return RISCV_EXCP_NONE;
2053}
2054
2055static RISCVException write_mstateen0(CPURISCVState *env, int csrno,
2056                                      target_ulong new_val)
2057{
2058    uint64_t wr_mask = SMSTATEEN_STATEEN | SMSTATEEN0_HSENVCFG;
2059
2060    return write_mstateen(env, csrno, wr_mask, new_val);
2061}
2062
2063static RISCVException write_mstateen_1_3(CPURISCVState *env, int csrno,
2064                                         target_ulong new_val)
2065{
2066    return write_mstateen(env, csrno, SMSTATEEN_STATEEN, new_val);
2067}
2068
2069static RISCVException read_mstateenh(CPURISCVState *env, int csrno,
2070                                     target_ulong *val)
2071{
2072    *val = env->mstateen[csrno - CSR_MSTATEEN0H] >> 32;
2073
2074    return RISCV_EXCP_NONE;
2075}
2076
2077static RISCVException write_mstateenh(CPURISCVState *env, int csrno,
2078                                      uint64_t wr_mask, target_ulong new_val)
2079{
2080    uint64_t *reg, val;
2081
2082    reg = &env->mstateen[csrno - CSR_MSTATEEN0H];
2083    val = (uint64_t)new_val << 32;
2084    val |= *reg & 0xFFFFFFFF;
2085    *reg = (*reg & ~wr_mask) | (val & wr_mask);
2086
2087    return RISCV_EXCP_NONE;
2088}
2089
2090static RISCVException write_mstateen0h(CPURISCVState *env, int csrno,
2091                                       target_ulong new_val)
2092{
2093    uint64_t wr_mask = SMSTATEEN_STATEEN | SMSTATEEN0_HSENVCFG;
2094
2095    return write_mstateenh(env, csrno, wr_mask, new_val);
2096}
2097
2098static RISCVException write_mstateenh_1_3(CPURISCVState *env, int csrno,
2099                                          target_ulong new_val)
2100{
2101    return write_mstateenh(env, csrno, SMSTATEEN_STATEEN, new_val);
2102}
2103
2104static RISCVException read_hstateen(CPURISCVState *env, int csrno,
2105                                    target_ulong *val)
2106{
2107    int index = csrno - CSR_HSTATEEN0;
2108
2109    *val = env->hstateen[index] & env->mstateen[index];
2110
2111    return RISCV_EXCP_NONE;
2112}
2113
2114static RISCVException write_hstateen(CPURISCVState *env, int csrno,
2115                                     uint64_t mask, target_ulong new_val)
2116{
2117    int index = csrno - CSR_HSTATEEN0;
2118    uint64_t *reg, wr_mask;
2119
2120    reg = &env->hstateen[index];
2121    wr_mask = env->mstateen[index] & mask;
2122    *reg = (*reg & ~wr_mask) | (new_val & wr_mask);
2123
2124    return RISCV_EXCP_NONE;
2125}
2126
2127static RISCVException write_hstateen0(CPURISCVState *env, int csrno,
2128                                      target_ulong new_val)
2129{
2130    uint64_t wr_mask = SMSTATEEN_STATEEN | SMSTATEEN0_HSENVCFG;
2131
2132    return write_hstateen(env, csrno, wr_mask, new_val);
2133}
2134
2135static RISCVException write_hstateen_1_3(CPURISCVState *env, int csrno,
2136                                         target_ulong new_val)
2137{
2138    return write_hstateen(env, csrno, SMSTATEEN_STATEEN, new_val);
2139}
2140
2141static RISCVException read_hstateenh(CPURISCVState *env, int csrno,
2142                                     target_ulong *val)
2143{
2144    int index = csrno - CSR_HSTATEEN0H;
2145
2146    *val = (env->hstateen[index] >> 32) & (env->mstateen[index] >> 32);
2147
2148    return RISCV_EXCP_NONE;
2149}
2150
2151static RISCVException write_hstateenh(CPURISCVState *env, int csrno,
2152                                      uint64_t mask, target_ulong new_val)
2153{
2154    int index = csrno - CSR_HSTATEEN0H;
2155    uint64_t *reg, wr_mask, val;
2156
2157    reg = &env->hstateen[index];
2158    val = (uint64_t)new_val << 32;
2159    val |= *reg & 0xFFFFFFFF;
2160    wr_mask = env->mstateen[index] & mask;
2161    *reg = (*reg & ~wr_mask) | (val & wr_mask);
2162
2163    return RISCV_EXCP_NONE;
2164}
2165
2166static RISCVException write_hstateen0h(CPURISCVState *env, int csrno,
2167                                       target_ulong new_val)
2168{
2169    uint64_t wr_mask = SMSTATEEN_STATEEN | SMSTATEEN0_HSENVCFG;
2170
2171    return write_hstateenh(env, csrno, wr_mask, new_val);
2172}
2173
2174static RISCVException write_hstateenh_1_3(CPURISCVState *env, int csrno,
2175                                          target_ulong new_val)
2176{
2177    return write_hstateenh(env, csrno, SMSTATEEN_STATEEN, new_val);
2178}
2179
2180static RISCVException read_sstateen(CPURISCVState *env, int csrno,
2181                                    target_ulong *val)
2182{
2183    bool virt = riscv_cpu_virt_enabled(env);
2184    int index = csrno - CSR_SSTATEEN0;
2185
2186    *val = env->sstateen[index] & env->mstateen[index];
2187    if (virt) {
2188        *val &= env->hstateen[index];
2189    }
2190
2191    return RISCV_EXCP_NONE;
2192}
2193
2194static RISCVException write_sstateen(CPURISCVState *env, int csrno,
2195                                     uint64_t mask, target_ulong new_val)
2196{
2197    bool virt = riscv_cpu_virt_enabled(env);
2198    int index = csrno - CSR_SSTATEEN0;
2199    uint64_t wr_mask;
2200    uint64_t *reg;
2201
2202    wr_mask = env->mstateen[index] & mask;
2203    if (virt) {
2204        wr_mask &= env->hstateen[index];
2205    }
2206
2207    reg = &env->sstateen[index];
2208    *reg = (*reg & ~wr_mask) | (new_val & wr_mask);
2209
2210    return RISCV_EXCP_NONE;
2211}
2212
2213static RISCVException write_sstateen0(CPURISCVState *env, int csrno,
2214                                      target_ulong new_val)
2215{
2216    uint64_t wr_mask = SMSTATEEN_STATEEN | SMSTATEEN0_HSENVCFG;
2217
2218    return write_sstateen(env, csrno, wr_mask, new_val);
2219}
2220
2221static RISCVException write_sstateen_1_3(CPURISCVState *env, int csrno,
2222                                      target_ulong new_val)
2223{
2224    return write_sstateen(env, csrno, SMSTATEEN_STATEEN, new_val);
2225}
2226
2227static RISCVException rmw_mip64(CPURISCVState *env, int csrno,
2228                                uint64_t *ret_val,
2229                                uint64_t new_val, uint64_t wr_mask)
2230{
2231    RISCVCPU *cpu = env_archcpu(env);
2232    uint64_t old_mip, mask = wr_mask & delegable_ints;
2233    uint32_t gin;
2234
2235    if (mask & MIP_SEIP) {
2236        env->software_seip = new_val & MIP_SEIP;
2237        new_val |= env->external_seip * MIP_SEIP;
2238    }
2239
2240    if (cpu->cfg.ext_sstc && (env->priv == PRV_M) &&
2241        get_field(env->menvcfg, MENVCFG_STCE)) {
2242        /* sstc extension forbids STIP & VSTIP to be writeable in mip */
2243        mask = mask & ~(MIP_STIP | MIP_VSTIP);
2244    }
2245
2246    if (mask) {
2247        old_mip = riscv_cpu_update_mip(cpu, mask, (new_val & mask));
2248    } else {
2249        old_mip = env->mip;
2250    }
2251
2252    if (csrno != CSR_HVIP) {
2253        gin = get_field(env->hstatus, HSTATUS_VGEIN);
2254        old_mip |= (env->hgeip & ((target_ulong)1 << gin)) ? MIP_VSEIP : 0;
2255        old_mip |= env->vstime_irq ? MIP_VSTIP : 0;
2256    }
2257
2258    if (ret_val) {
2259        *ret_val = old_mip;
2260    }
2261
2262    return RISCV_EXCP_NONE;
2263}
2264
2265static RISCVException rmw_mip(CPURISCVState *env, int csrno,
2266                              target_ulong *ret_val,
2267                              target_ulong new_val, target_ulong wr_mask)
2268{
2269    uint64_t rval;
2270    RISCVException ret;
2271
2272    ret = rmw_mip64(env, csrno, &rval, new_val, wr_mask);
2273    if (ret_val) {
2274        *ret_val = rval;
2275    }
2276
2277    return ret;
2278}
2279
2280static RISCVException rmw_miph(CPURISCVState *env, int csrno,
2281                               target_ulong *ret_val,
2282                               target_ulong new_val, target_ulong wr_mask)
2283{
2284    uint64_t rval;
2285    RISCVException ret;
2286
2287    ret = rmw_mip64(env, csrno, &rval,
2288        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2289    if (ret_val) {
2290        *ret_val = rval >> 32;
2291    }
2292
2293    return ret;
2294}
2295
2296/* Supervisor Trap Setup */
2297static RISCVException read_sstatus_i128(CPURISCVState *env, int csrno,
2298                                        Int128 *val)
2299{
2300    uint64_t mask = sstatus_v1_10_mask;
2301    uint64_t sstatus = env->mstatus & mask;
2302    if (env->xl != MXL_RV32 || env->debugger) {
2303        mask |= SSTATUS64_UXL;
2304    }
2305
2306    *val = int128_make128(sstatus, add_status_sd(MXL_RV128, sstatus));
2307    return RISCV_EXCP_NONE;
2308}
2309
2310static RISCVException read_sstatus(CPURISCVState *env, int csrno,
2311                                   target_ulong *val)
2312{
2313    target_ulong mask = (sstatus_v1_10_mask);
2314    if (env->xl != MXL_RV32 || env->debugger) {
2315        mask |= SSTATUS64_UXL;
2316    }
2317    /* TODO: Use SXL not MXL. */
2318    *val = add_status_sd(riscv_cpu_mxl(env), env->mstatus & mask);
2319    return RISCV_EXCP_NONE;
2320}
2321
2322static RISCVException write_sstatus(CPURISCVState *env, int csrno,
2323                                    target_ulong val)
2324{
2325    target_ulong mask = (sstatus_v1_10_mask);
2326
2327    if (env->xl != MXL_RV32 || env->debugger) {
2328        if ((val & SSTATUS64_UXL) != 0) {
2329            mask |= SSTATUS64_UXL;
2330        }
2331    }
2332    target_ulong newval = (env->mstatus & ~mask) | (val & mask);
2333    return write_mstatus(env, CSR_MSTATUS, newval);
2334}
2335
2336static RISCVException rmw_vsie64(CPURISCVState *env, int csrno,
2337                                 uint64_t *ret_val,
2338                                 uint64_t new_val, uint64_t wr_mask)
2339{
2340    RISCVException ret;
2341    uint64_t rval, mask = env->hideleg & VS_MODE_INTERRUPTS;
2342
2343    /* Bring VS-level bits to correct position */
2344    new_val = (new_val & (VS_MODE_INTERRUPTS >> 1)) << 1;
2345    wr_mask = (wr_mask & (VS_MODE_INTERRUPTS >> 1)) << 1;
2346
2347    ret = rmw_mie64(env, csrno, &rval, new_val, wr_mask & mask);
2348    if (ret_val) {
2349        *ret_val = (rval & mask) >> 1;
2350    }
2351
2352    return ret;
2353}
2354
2355static RISCVException rmw_vsie(CPURISCVState *env, int csrno,
2356                               target_ulong *ret_val,
2357                               target_ulong new_val, target_ulong wr_mask)
2358{
2359    uint64_t rval;
2360    RISCVException ret;
2361
2362    ret = rmw_vsie64(env, csrno, &rval, new_val, wr_mask);
2363    if (ret_val) {
2364        *ret_val = rval;
2365    }
2366
2367    return ret;
2368}
2369
2370static RISCVException rmw_vsieh(CPURISCVState *env, int csrno,
2371                                target_ulong *ret_val,
2372                                target_ulong new_val, target_ulong wr_mask)
2373{
2374    uint64_t rval;
2375    RISCVException ret;
2376
2377    ret = rmw_vsie64(env, csrno, &rval,
2378        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2379    if (ret_val) {
2380        *ret_val = rval >> 32;
2381    }
2382
2383    return ret;
2384}
2385
2386static RISCVException rmw_sie64(CPURISCVState *env, int csrno,
2387                                uint64_t *ret_val,
2388                                uint64_t new_val, uint64_t wr_mask)
2389{
2390    RISCVException ret;
2391    uint64_t mask = env->mideleg & S_MODE_INTERRUPTS;
2392
2393    if (riscv_cpu_virt_enabled(env)) {
2394        if (env->hvictl & HVICTL_VTI) {
2395            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
2396        }
2397        ret = rmw_vsie64(env, CSR_VSIE, ret_val, new_val, wr_mask);
2398    } else {
2399        ret = rmw_mie64(env, csrno, ret_val, new_val, wr_mask & mask);
2400    }
2401
2402    if (ret_val) {
2403        *ret_val &= mask;
2404    }
2405
2406    return ret;
2407}
2408
2409static RISCVException rmw_sie(CPURISCVState *env, int csrno,
2410                              target_ulong *ret_val,
2411                              target_ulong new_val, target_ulong wr_mask)
2412{
2413    uint64_t rval;
2414    RISCVException ret;
2415
2416    ret = rmw_sie64(env, csrno, &rval, new_val, wr_mask);
2417    if (ret == RISCV_EXCP_NONE && ret_val) {
2418        *ret_val = rval;
2419    }
2420
2421    return ret;
2422}
2423
2424static RISCVException rmw_sieh(CPURISCVState *env, int csrno,
2425                               target_ulong *ret_val,
2426                               target_ulong new_val, target_ulong wr_mask)
2427{
2428    uint64_t rval;
2429    RISCVException ret;
2430
2431    ret = rmw_sie64(env, csrno, &rval,
2432        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2433    if (ret_val) {
2434        *ret_val = rval >> 32;
2435    }
2436
2437    return ret;
2438}
2439
2440static RISCVException read_stvec(CPURISCVState *env, int csrno,
2441                                 target_ulong *val)
2442{
2443    *val = env->stvec;
2444    return RISCV_EXCP_NONE;
2445}
2446
2447static RISCVException write_stvec(CPURISCVState *env, int csrno,
2448                                  target_ulong val)
2449{
2450    /* bits [1:0] encode mode; 0 = direct, 1 = vectored, 2 >= reserved */
2451    if ((val & 3) < 2) {
2452        env->stvec = val;
2453    } else {
2454        qemu_log_mask(LOG_UNIMP, "CSR_STVEC: reserved mode not supported\n");
2455    }
2456    return RISCV_EXCP_NONE;
2457}
2458
2459static RISCVException read_scounteren(CPURISCVState *env, int csrno,
2460                                      target_ulong *val)
2461{
2462    *val = env->scounteren;
2463    return RISCV_EXCP_NONE;
2464}
2465
2466static RISCVException write_scounteren(CPURISCVState *env, int csrno,
2467                                       target_ulong val)
2468{
2469    env->scounteren = val;
2470    return RISCV_EXCP_NONE;
2471}
2472
2473/* Supervisor Trap Handling */
2474static RISCVException read_sscratch_i128(CPURISCVState *env, int csrno,
2475                                         Int128 *val)
2476{
2477    *val = int128_make128(env->sscratch, env->sscratchh);
2478    return RISCV_EXCP_NONE;
2479}
2480
2481static RISCVException write_sscratch_i128(CPURISCVState *env, int csrno,
2482                                          Int128 val)
2483{
2484    env->sscratch = int128_getlo(val);
2485    env->sscratchh = int128_gethi(val);
2486    return RISCV_EXCP_NONE;
2487}
2488
2489static RISCVException read_sscratch(CPURISCVState *env, int csrno,
2490                                    target_ulong *val)
2491{
2492    *val = env->sscratch;
2493    return RISCV_EXCP_NONE;
2494}
2495
2496static RISCVException write_sscratch(CPURISCVState *env, int csrno,
2497                                     target_ulong val)
2498{
2499    env->sscratch = val;
2500    return RISCV_EXCP_NONE;
2501}
2502
2503static RISCVException read_sepc(CPURISCVState *env, int csrno,
2504                                target_ulong *val)
2505{
2506    *val = env->sepc;
2507    return RISCV_EXCP_NONE;
2508}
2509
2510static RISCVException write_sepc(CPURISCVState *env, int csrno,
2511                                 target_ulong val)
2512{
2513    env->sepc = val;
2514    return RISCV_EXCP_NONE;
2515}
2516
2517static RISCVException read_scause(CPURISCVState *env, int csrno,
2518                                  target_ulong *val)
2519{
2520    *val = env->scause;
2521    return RISCV_EXCP_NONE;
2522}
2523
2524static RISCVException write_scause(CPURISCVState *env, int csrno,
2525                                   target_ulong val)
2526{
2527    env->scause = val;
2528    return RISCV_EXCP_NONE;
2529}
2530
2531static RISCVException read_stval(CPURISCVState *env, int csrno,
2532                                 target_ulong *val)
2533{
2534    *val = env->stval;
2535    return RISCV_EXCP_NONE;
2536}
2537
2538static RISCVException write_stval(CPURISCVState *env, int csrno,
2539                                  target_ulong val)
2540{
2541    env->stval = val;
2542    return RISCV_EXCP_NONE;
2543}
2544
2545static RISCVException rmw_vsip64(CPURISCVState *env, int csrno,
2546                                 uint64_t *ret_val,
2547                                 uint64_t new_val, uint64_t wr_mask)
2548{
2549    RISCVException ret;
2550    uint64_t rval, mask = env->hideleg & VS_MODE_INTERRUPTS;
2551
2552    /* Bring VS-level bits to correct position */
2553    new_val = (new_val & (VS_MODE_INTERRUPTS >> 1)) << 1;
2554    wr_mask = (wr_mask & (VS_MODE_INTERRUPTS >> 1)) << 1;
2555
2556    ret = rmw_mip64(env, csrno, &rval, new_val,
2557                    wr_mask & mask & vsip_writable_mask);
2558    if (ret_val) {
2559        *ret_val = (rval & mask) >> 1;
2560    }
2561
2562    return ret;
2563}
2564
2565static RISCVException rmw_vsip(CPURISCVState *env, int csrno,
2566                               target_ulong *ret_val,
2567                               target_ulong new_val, target_ulong wr_mask)
2568{
2569    uint64_t rval;
2570    RISCVException ret;
2571
2572    ret = rmw_vsip64(env, csrno, &rval, new_val, wr_mask);
2573    if (ret_val) {
2574        *ret_val = rval;
2575    }
2576
2577    return ret;
2578}
2579
2580static RISCVException rmw_vsiph(CPURISCVState *env, int csrno,
2581                                target_ulong *ret_val,
2582                                target_ulong new_val, target_ulong wr_mask)
2583{
2584    uint64_t rval;
2585    RISCVException ret;
2586
2587    ret = rmw_vsip64(env, csrno, &rval,
2588        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2589    if (ret_val) {
2590        *ret_val = rval >> 32;
2591    }
2592
2593    return ret;
2594}
2595
2596static RISCVException rmw_sip64(CPURISCVState *env, int csrno,
2597                                uint64_t *ret_val,
2598                                uint64_t new_val, uint64_t wr_mask)
2599{
2600    RISCVException ret;
2601    uint64_t mask = env->mideleg & sip_writable_mask;
2602
2603    if (riscv_cpu_virt_enabled(env)) {
2604        if (env->hvictl & HVICTL_VTI) {
2605            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
2606        }
2607        ret = rmw_vsip64(env, CSR_VSIP, ret_val, new_val, wr_mask);
2608    } else {
2609        ret = rmw_mip64(env, csrno, ret_val, new_val, wr_mask & mask);
2610    }
2611
2612    if (ret_val) {
2613        *ret_val &= env->mideleg & S_MODE_INTERRUPTS;
2614    }
2615
2616    return ret;
2617}
2618
2619static RISCVException rmw_sip(CPURISCVState *env, int csrno,
2620                              target_ulong *ret_val,
2621                              target_ulong new_val, target_ulong wr_mask)
2622{
2623    uint64_t rval;
2624    RISCVException ret;
2625
2626    ret = rmw_sip64(env, csrno, &rval, new_val, wr_mask);
2627    if (ret_val) {
2628        *ret_val = rval;
2629    }
2630
2631    return ret;
2632}
2633
2634static RISCVException rmw_siph(CPURISCVState *env, int csrno,
2635                               target_ulong *ret_val,
2636                               target_ulong new_val, target_ulong wr_mask)
2637{
2638    uint64_t rval;
2639    RISCVException ret;
2640
2641    ret = rmw_sip64(env, csrno, &rval,
2642        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2643    if (ret_val) {
2644        *ret_val = rval >> 32;
2645    }
2646
2647    return ret;
2648}
2649
2650/* Supervisor Protection and Translation */
2651static RISCVException read_satp(CPURISCVState *env, int csrno,
2652                                target_ulong *val)
2653{
2654    if (!riscv_cpu_cfg(env)->mmu) {
2655        *val = 0;
2656        return RISCV_EXCP_NONE;
2657    }
2658
2659    if (env->priv == PRV_S && get_field(env->mstatus, MSTATUS_TVM)) {
2660        return RISCV_EXCP_ILLEGAL_INST;
2661    } else {
2662        *val = env->satp;
2663    }
2664
2665    return RISCV_EXCP_NONE;
2666}
2667
2668static RISCVException write_satp(CPURISCVState *env, int csrno,
2669                                 target_ulong val)
2670{
2671    target_ulong mask;
2672    bool vm;
2673
2674    if (!riscv_cpu_cfg(env)->mmu) {
2675        return RISCV_EXCP_NONE;
2676    }
2677
2678    if (riscv_cpu_mxl(env) == MXL_RV32) {
2679        vm = validate_vm(env, get_field(val, SATP32_MODE));
2680        mask = (val ^ env->satp) & (SATP32_MODE | SATP32_ASID | SATP32_PPN);
2681    } else {
2682        vm = validate_vm(env, get_field(val, SATP64_MODE));
2683        mask = (val ^ env->satp) & (SATP64_MODE | SATP64_ASID | SATP64_PPN);
2684    }
2685
2686    if (vm && mask) {
2687        if (env->priv == PRV_S && get_field(env->mstatus, MSTATUS_TVM)) {
2688            return RISCV_EXCP_ILLEGAL_INST;
2689        } else {
2690            /*
2691             * The ISA defines SATP.MODE=Bare as "no translation", but we still
2692             * pass these through QEMU's TLB emulation as it improves
2693             * performance.  Flushing the TLB on SATP writes with paging
2694             * enabled avoids leaking those invalid cached mappings.
2695             */
2696            tlb_flush(env_cpu(env));
2697            env->satp = val;
2698        }
2699    }
2700    return RISCV_EXCP_NONE;
2701}
2702
2703static int read_vstopi(CPURISCVState *env, int csrno, target_ulong *val)
2704{
2705    int irq, ret;
2706    target_ulong topei;
2707    uint64_t vseip, vsgein;
2708    uint32_t iid, iprio, hviid, hviprio, gein;
2709    uint32_t s, scount = 0, siid[VSTOPI_NUM_SRCS], siprio[VSTOPI_NUM_SRCS];
2710
2711    gein = get_field(env->hstatus, HSTATUS_VGEIN);
2712    hviid = get_field(env->hvictl, HVICTL_IID);
2713    hviprio = get_field(env->hvictl, HVICTL_IPRIO);
2714
2715    if (gein) {
2716        vsgein = (env->hgeip & (1ULL << gein)) ? MIP_VSEIP : 0;
2717        vseip = env->mie & (env->mip | vsgein) & MIP_VSEIP;
2718        if (gein <= env->geilen && vseip) {
2719            siid[scount] = IRQ_S_EXT;
2720            siprio[scount] = IPRIO_MMAXIPRIO + 1;
2721            if (env->aia_ireg_rmw_fn[PRV_S]) {
2722                /*
2723                 * Call machine specific IMSIC register emulation for
2724                 * reading TOPEI.
2725                 */
2726                ret = env->aia_ireg_rmw_fn[PRV_S](
2727                        env->aia_ireg_rmw_fn_arg[PRV_S],
2728                        AIA_MAKE_IREG(ISELECT_IMSIC_TOPEI, PRV_S, true, gein,
2729                                      riscv_cpu_mxl_bits(env)),
2730                        &topei, 0, 0);
2731                if (!ret && topei) {
2732                    siprio[scount] = topei & IMSIC_TOPEI_IPRIO_MASK;
2733                }
2734            }
2735            scount++;
2736        }
2737    } else {
2738        if (hviid == IRQ_S_EXT && hviprio) {
2739            siid[scount] = IRQ_S_EXT;
2740            siprio[scount] = hviprio;
2741            scount++;
2742        }
2743    }
2744
2745    if (env->hvictl & HVICTL_VTI) {
2746        if (hviid != IRQ_S_EXT) {
2747            siid[scount] = hviid;
2748            siprio[scount] = hviprio;
2749            scount++;
2750        }
2751    } else {
2752        irq = riscv_cpu_vsirq_pending(env);
2753        if (irq != IRQ_S_EXT && 0 < irq && irq <= 63) {
2754            siid[scount] = irq;
2755            siprio[scount] = env->hviprio[irq];
2756            scount++;
2757        }
2758    }
2759
2760    iid = 0;
2761    iprio = UINT_MAX;
2762    for (s = 0; s < scount; s++) {
2763        if (siprio[s] < iprio) {
2764            iid = siid[s];
2765            iprio = siprio[s];
2766        }
2767    }
2768
2769    if (iid) {
2770        if (env->hvictl & HVICTL_IPRIOM) {
2771            if (iprio > IPRIO_MMAXIPRIO) {
2772                iprio = IPRIO_MMAXIPRIO;
2773            }
2774            if (!iprio) {
2775                if (riscv_cpu_default_priority(iid) > IPRIO_DEFAULT_S) {
2776                    iprio = IPRIO_MMAXIPRIO;
2777                }
2778            }
2779        } else {
2780            iprio = 1;
2781        }
2782    } else {
2783        iprio = 0;
2784    }
2785
2786    *val = (iid & TOPI_IID_MASK) << TOPI_IID_SHIFT;
2787    *val |= iprio;
2788    return RISCV_EXCP_NONE;
2789}
2790
2791static int read_stopi(CPURISCVState *env, int csrno, target_ulong *val)
2792{
2793    int irq;
2794    uint8_t iprio;
2795
2796    if (riscv_cpu_virt_enabled(env)) {
2797        return read_vstopi(env, CSR_VSTOPI, val);
2798    }
2799
2800    irq = riscv_cpu_sirq_pending(env);
2801    if (irq <= 0 || irq > 63) {
2802        *val = 0;
2803    } else {
2804        iprio = env->siprio[irq];
2805        if (!iprio) {
2806            if (riscv_cpu_default_priority(irq) > IPRIO_DEFAULT_S) {
2807                iprio = IPRIO_MMAXIPRIO;
2808           }
2809        }
2810        *val = (irq & TOPI_IID_MASK) << TOPI_IID_SHIFT;
2811        *val |= iprio;
2812    }
2813
2814    return RISCV_EXCP_NONE;
2815}
2816
2817/* Hypervisor Extensions */
2818static RISCVException read_hstatus(CPURISCVState *env, int csrno,
2819                                   target_ulong *val)
2820{
2821    *val = env->hstatus;
2822    if (riscv_cpu_mxl(env) != MXL_RV32) {
2823        /* We only support 64-bit VSXL */
2824        *val = set_field(*val, HSTATUS_VSXL, 2);
2825    }
2826    /* We only support little endian */
2827    *val = set_field(*val, HSTATUS_VSBE, 0);
2828    return RISCV_EXCP_NONE;
2829}
2830
2831static RISCVException write_hstatus(CPURISCVState *env, int csrno,
2832                                    target_ulong val)
2833{
2834    env->hstatus = val;
2835    if (riscv_cpu_mxl(env) != MXL_RV32 && get_field(val, HSTATUS_VSXL) != 2) {
2836        qemu_log_mask(LOG_UNIMP, "QEMU does not support mixed HSXLEN options.");
2837    }
2838    if (get_field(val, HSTATUS_VSBE) != 0) {
2839        qemu_log_mask(LOG_UNIMP, "QEMU does not support big endian guests.");
2840    }
2841    return RISCV_EXCP_NONE;
2842}
2843
2844static RISCVException read_hedeleg(CPURISCVState *env, int csrno,
2845                                   target_ulong *val)
2846{
2847    *val = env->hedeleg;
2848    return RISCV_EXCP_NONE;
2849}
2850
2851static RISCVException write_hedeleg(CPURISCVState *env, int csrno,
2852                                    target_ulong val)
2853{
2854    env->hedeleg = val & vs_delegable_excps;
2855    return RISCV_EXCP_NONE;
2856}
2857
2858static RISCVException rmw_hideleg64(CPURISCVState *env, int csrno,
2859                                    uint64_t *ret_val,
2860                                    uint64_t new_val, uint64_t wr_mask)
2861{
2862    uint64_t mask = wr_mask & vs_delegable_ints;
2863
2864    if (ret_val) {
2865        *ret_val = env->hideleg & vs_delegable_ints;
2866    }
2867
2868    env->hideleg = (env->hideleg & ~mask) | (new_val & mask);
2869    return RISCV_EXCP_NONE;
2870}
2871
2872static RISCVException rmw_hideleg(CPURISCVState *env, int csrno,
2873                                  target_ulong *ret_val,
2874                                  target_ulong new_val, target_ulong wr_mask)
2875{
2876    uint64_t rval;
2877    RISCVException ret;
2878
2879    ret = rmw_hideleg64(env, csrno, &rval, new_val, wr_mask);
2880    if (ret_val) {
2881        *ret_val = rval;
2882    }
2883
2884    return ret;
2885}
2886
2887static RISCVException rmw_hidelegh(CPURISCVState *env, int csrno,
2888                                   target_ulong *ret_val,
2889                                   target_ulong new_val, target_ulong wr_mask)
2890{
2891    uint64_t rval;
2892    RISCVException ret;
2893
2894    ret = rmw_hideleg64(env, csrno, &rval,
2895        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2896    if (ret_val) {
2897        *ret_val = rval >> 32;
2898    }
2899
2900    return ret;
2901}
2902
2903static RISCVException rmw_hvip64(CPURISCVState *env, int csrno,
2904                                 uint64_t *ret_val,
2905                                 uint64_t new_val, uint64_t wr_mask)
2906{
2907    RISCVException ret;
2908
2909    ret = rmw_mip64(env, csrno, ret_val, new_val,
2910                    wr_mask & hvip_writable_mask);
2911    if (ret_val) {
2912        *ret_val &= VS_MODE_INTERRUPTS;
2913    }
2914
2915    return ret;
2916}
2917
2918static RISCVException rmw_hvip(CPURISCVState *env, int csrno,
2919                               target_ulong *ret_val,
2920                               target_ulong new_val, target_ulong wr_mask)
2921{
2922    uint64_t rval;
2923    RISCVException ret;
2924
2925    ret = rmw_hvip64(env, csrno, &rval, new_val, wr_mask);
2926    if (ret_val) {
2927        *ret_val = rval;
2928    }
2929
2930    return ret;
2931}
2932
2933static RISCVException rmw_hviph(CPURISCVState *env, int csrno,
2934                                target_ulong *ret_val,
2935                                target_ulong new_val, target_ulong wr_mask)
2936{
2937    uint64_t rval;
2938    RISCVException ret;
2939
2940    ret = rmw_hvip64(env, csrno, &rval,
2941        ((uint64_t)new_val) << 32, ((uint64_t)wr_mask) << 32);
2942    if (ret_val) {
2943        *ret_val = rval >> 32;
2944    }
2945
2946    return ret;
2947}
2948
2949static RISCVException rmw_hip(CPURISCVState *env, int csrno,
2950                              target_ulong *ret_value,
2951                              target_ulong new_value, target_ulong write_mask)
2952{
2953    int ret = rmw_mip(env, csrno, ret_value, new_value,
2954                      write_mask & hip_writable_mask);
2955
2956    if (ret_value) {
2957        *ret_value &= HS_MODE_INTERRUPTS;
2958    }
2959    return ret;
2960}
2961
2962static RISCVException rmw_hie(CPURISCVState *env, int csrno,
2963                              target_ulong *ret_val,
2964                              target_ulong new_val, target_ulong wr_mask)
2965{
2966    uint64_t rval;
2967    RISCVException ret;
2968
2969    ret = rmw_mie64(env, csrno, &rval, new_val, wr_mask & HS_MODE_INTERRUPTS);
2970    if (ret_val) {
2971        *ret_val = rval & HS_MODE_INTERRUPTS;
2972    }
2973
2974    return ret;
2975}
2976
2977static RISCVException read_hcounteren(CPURISCVState *env, int csrno,
2978                                      target_ulong *val)
2979{
2980    *val = env->hcounteren;
2981    return RISCV_EXCP_NONE;
2982}
2983
2984static RISCVException write_hcounteren(CPURISCVState *env, int csrno,
2985                                       target_ulong val)
2986{
2987    env->hcounteren = val;
2988    return RISCV_EXCP_NONE;
2989}
2990
2991static RISCVException read_hgeie(CPURISCVState *env, int csrno,
2992                                 target_ulong *val)
2993{
2994    if (val) {
2995        *val = env->hgeie;
2996    }
2997    return RISCV_EXCP_NONE;
2998}
2999
3000static RISCVException write_hgeie(CPURISCVState *env, int csrno,
3001                                  target_ulong val)
3002{
3003    /* Only GEILEN:1 bits implemented and BIT0 is never implemented */
3004    val &= ((((target_ulong)1) << env->geilen) - 1) << 1;
3005    env->hgeie = val;
3006    /* Update mip.SGEIP bit */
3007    riscv_cpu_update_mip(env_archcpu(env), MIP_SGEIP,
3008                         BOOL_TO_MASK(!!(env->hgeie & env->hgeip)));
3009    return RISCV_EXCP_NONE;
3010}
3011
3012static RISCVException read_htval(CPURISCVState *env, int csrno,
3013                                 target_ulong *val)
3014{
3015    *val = env->htval;
3016    return RISCV_EXCP_NONE;
3017}
3018
3019static RISCVException write_htval(CPURISCVState *env, int csrno,
3020                                  target_ulong val)
3021{
3022    env->htval = val;
3023    return RISCV_EXCP_NONE;
3024}
3025
3026static RISCVException read_htinst(CPURISCVState *env, int csrno,
3027                                  target_ulong *val)
3028{
3029    *val = env->htinst;
3030    return RISCV_EXCP_NONE;
3031}
3032
3033static RISCVException write_htinst(CPURISCVState *env, int csrno,
3034                                   target_ulong val)
3035{
3036    return RISCV_EXCP_NONE;
3037}
3038
3039static RISCVException read_hgeip(CPURISCVState *env, int csrno,
3040                                 target_ulong *val)
3041{
3042    if (val) {
3043        *val = env->hgeip;
3044    }
3045    return RISCV_EXCP_NONE;
3046}
3047
3048static RISCVException read_hgatp(CPURISCVState *env, int csrno,
3049                                 target_ulong *val)
3050{
3051    *val = env->hgatp;
3052    return RISCV_EXCP_NONE;
3053}
3054
3055static RISCVException write_hgatp(CPURISCVState *env, int csrno,
3056                                  target_ulong val)
3057{
3058    env->hgatp = val;
3059    return RISCV_EXCP_NONE;
3060}
3061
3062static RISCVException read_htimedelta(CPURISCVState *env, int csrno,
3063                                      target_ulong *val)
3064{
3065    if (!env->rdtime_fn) {
3066        return RISCV_EXCP_ILLEGAL_INST;
3067    }
3068
3069    *val = env->htimedelta;
3070    return RISCV_EXCP_NONE;
3071}
3072
3073static RISCVException write_htimedelta(CPURISCVState *env, int csrno,
3074                                       target_ulong val)
3075{
3076    RISCVCPU *cpu = env_archcpu(env);
3077
3078    if (!env->rdtime_fn) {
3079        return RISCV_EXCP_ILLEGAL_INST;
3080    }
3081
3082    if (riscv_cpu_mxl(env) == MXL_RV32) {
3083        env->htimedelta = deposit64(env->htimedelta, 0, 32, (uint64_t)val);
3084    } else {
3085        env->htimedelta = val;
3086    }
3087
3088    if (cpu->cfg.ext_sstc && env->rdtime_fn) {
3089        riscv_timer_write_timecmp(cpu, env->vstimer, env->vstimecmp,
3090                                  env->htimedelta, MIP_VSTIP);
3091    }
3092
3093    return RISCV_EXCP_NONE;
3094}
3095
3096static RISCVException read_htimedeltah(CPURISCVState *env, int csrno,
3097                                       target_ulong *val)
3098{
3099    if (!env->rdtime_fn) {
3100        return RISCV_EXCP_ILLEGAL_INST;
3101    }
3102
3103    *val = env->htimedelta >> 32;
3104    return RISCV_EXCP_NONE;
3105}
3106
3107static RISCVException write_htimedeltah(CPURISCVState *env, int csrno,
3108                                        target_ulong val)
3109{
3110    RISCVCPU *cpu = env_archcpu(env);
3111
3112    if (!env->rdtime_fn) {
3113        return RISCV_EXCP_ILLEGAL_INST;
3114    }
3115
3116    env->htimedelta = deposit64(env->htimedelta, 32, 32, (uint64_t)val);
3117
3118    if (cpu->cfg.ext_sstc && env->rdtime_fn) {
3119        riscv_timer_write_timecmp(cpu, env->vstimer, env->vstimecmp,
3120                                  env->htimedelta, MIP_VSTIP);
3121    }
3122
3123    return RISCV_EXCP_NONE;
3124}
3125
3126static int read_hvictl(CPURISCVState *env, int csrno, target_ulong *val)
3127{
3128    *val = env->hvictl;
3129    return RISCV_EXCP_NONE;
3130}
3131
3132static int write_hvictl(CPURISCVState *env, int csrno, target_ulong val)
3133{
3134    env->hvictl = val & HVICTL_VALID_MASK;
3135    return RISCV_EXCP_NONE;
3136}
3137
3138static int read_hvipriox(CPURISCVState *env, int first_index,
3139                         uint8_t *iprio, target_ulong *val)
3140{
3141    int i, irq, rdzero, num_irqs = 4 * (riscv_cpu_mxl_bits(env) / 32);
3142
3143    /* First index has to be a multiple of number of irqs per register */
3144    if (first_index % num_irqs) {
3145        return (riscv_cpu_virt_enabled(env)) ?
3146               RISCV_EXCP_VIRT_INSTRUCTION_FAULT : RISCV_EXCP_ILLEGAL_INST;
3147    }
3148
3149    /* Fill-up return value */
3150    *val = 0;
3151    for (i = 0; i < num_irqs; i++) {
3152        if (riscv_cpu_hviprio_index2irq(first_index + i, &irq, &rdzero)) {
3153            continue;
3154        }
3155        if (rdzero) {
3156            continue;
3157        }
3158        *val |= ((target_ulong)iprio[irq]) << (i * 8);
3159    }
3160
3161    return RISCV_EXCP_NONE;
3162}
3163
3164static int write_hvipriox(CPURISCVState *env, int first_index,
3165                          uint8_t *iprio, target_ulong val)
3166{
3167    int i, irq, rdzero, num_irqs = 4 * (riscv_cpu_mxl_bits(env) / 32);
3168
3169    /* First index has to be a multiple of number of irqs per register */
3170    if (first_index % num_irqs) {
3171        return (riscv_cpu_virt_enabled(env)) ?
3172               RISCV_EXCP_VIRT_INSTRUCTION_FAULT : RISCV_EXCP_ILLEGAL_INST;
3173    }
3174
3175    /* Fill-up priority arrary */
3176    for (i = 0; i < num_irqs; i++) {
3177        if (riscv_cpu_hviprio_index2irq(first_index + i, &irq, &rdzero)) {
3178            continue;
3179        }
3180        if (rdzero) {
3181            iprio[irq] = 0;
3182        } else {
3183            iprio[irq] = (val >> (i * 8)) & 0xff;
3184        }
3185    }
3186
3187    return RISCV_EXCP_NONE;
3188}
3189
3190static int read_hviprio1(CPURISCVState *env, int csrno, target_ulong *val)
3191{
3192    return read_hvipriox(env, 0, env->hviprio, val);
3193}
3194
3195static int write_hviprio1(CPURISCVState *env, int csrno, target_ulong val)
3196{
3197    return write_hvipriox(env, 0, env->hviprio, val);
3198}
3199
3200static int read_hviprio1h(CPURISCVState *env, int csrno, target_ulong *val)
3201{
3202    return read_hvipriox(env, 4, env->hviprio, val);
3203}
3204
3205static int write_hviprio1h(CPURISCVState *env, int csrno, target_ulong val)
3206{
3207    return write_hvipriox(env, 4, env->hviprio, val);
3208}
3209
3210static int read_hviprio2(CPURISCVState *env, int csrno, target_ulong *val)
3211{
3212    return read_hvipriox(env, 8, env->hviprio, val);
3213}
3214
3215static int write_hviprio2(CPURISCVState *env, int csrno, target_ulong val)
3216{
3217    return write_hvipriox(env, 8, env->hviprio, val);
3218}
3219
3220static int read_hviprio2h(CPURISCVState *env, int csrno, target_ulong *val)
3221{
3222    return read_hvipriox(env, 12, env->hviprio, val);
3223}
3224
3225static int write_hviprio2h(CPURISCVState *env, int csrno, target_ulong val)
3226{
3227    return write_hvipriox(env, 12, env->hviprio, val);
3228}
3229
3230/* Virtual CSR Registers */
3231static RISCVException read_vsstatus(CPURISCVState *env, int csrno,
3232                                    target_ulong *val)
3233{
3234    *val = env->vsstatus;
3235    return RISCV_EXCP_NONE;
3236}
3237
3238static RISCVException write_vsstatus(CPURISCVState *env, int csrno,
3239                                     target_ulong val)
3240{
3241    uint64_t mask = (target_ulong)-1;
3242    if ((val & VSSTATUS64_UXL) == 0) {
3243        mask &= ~VSSTATUS64_UXL;
3244    }
3245    env->vsstatus = (env->vsstatus & ~mask) | (uint64_t)val;
3246    return RISCV_EXCP_NONE;
3247}
3248
3249static int read_vstvec(CPURISCVState *env, int csrno, target_ulong *val)
3250{
3251    *val = env->vstvec;
3252    return RISCV_EXCP_NONE;
3253}
3254
3255static RISCVException write_vstvec(CPURISCVState *env, int csrno,
3256                                   target_ulong val)
3257{
3258    env->vstvec = val;
3259    return RISCV_EXCP_NONE;
3260}
3261
3262static RISCVException read_vsscratch(CPURISCVState *env, int csrno,
3263                                     target_ulong *val)
3264{
3265    *val = env->vsscratch;
3266    return RISCV_EXCP_NONE;
3267}
3268
3269static RISCVException write_vsscratch(CPURISCVState *env, int csrno,
3270                                      target_ulong val)
3271{
3272    env->vsscratch = val;
3273    return RISCV_EXCP_NONE;
3274}
3275
3276static RISCVException read_vsepc(CPURISCVState *env, int csrno,
3277                                 target_ulong *val)
3278{
3279    *val = env->vsepc;
3280    return RISCV_EXCP_NONE;
3281}
3282
3283static RISCVException write_vsepc(CPURISCVState *env, int csrno,
3284                                  target_ulong val)
3285{
3286    env->vsepc = val;
3287    return RISCV_EXCP_NONE;
3288}
3289
3290static RISCVException read_vscause(CPURISCVState *env, int csrno,
3291                                   target_ulong *val)
3292{
3293    *val = env->vscause;
3294    return RISCV_EXCP_NONE;
3295}
3296
3297static RISCVException write_vscause(CPURISCVState *env, int csrno,
3298                                    target_ulong val)
3299{
3300    env->vscause = val;
3301    return RISCV_EXCP_NONE;
3302}
3303
3304static RISCVException read_vstval(CPURISCVState *env, int csrno,
3305                                  target_ulong *val)
3306{
3307    *val = env->vstval;
3308    return RISCV_EXCP_NONE;
3309}
3310
3311static RISCVException write_vstval(CPURISCVState *env, int csrno,
3312                                   target_ulong val)
3313{
3314    env->vstval = val;
3315    return RISCV_EXCP_NONE;
3316}
3317
3318static RISCVException read_vsatp(CPURISCVState *env, int csrno,
3319                                 target_ulong *val)
3320{
3321    *val = env->vsatp;
3322    return RISCV_EXCP_NONE;
3323}
3324
3325static RISCVException write_vsatp(CPURISCVState *env, int csrno,
3326                                  target_ulong val)
3327{
3328    env->vsatp = val;
3329    return RISCV_EXCP_NONE;
3330}
3331
3332static RISCVException read_mtval2(CPURISCVState *env, int csrno,
3333                                  target_ulong *val)
3334{
3335    *val = env->mtval2;
3336    return RISCV_EXCP_NONE;
3337}
3338
3339static RISCVException write_mtval2(CPURISCVState *env, int csrno,
3340                                   target_ulong val)
3341{
3342    env->mtval2 = val;
3343    return RISCV_EXCP_NONE;
3344}
3345
3346static RISCVException read_mtinst(CPURISCVState *env, int csrno,
3347                                  target_ulong *val)
3348{
3349    *val = env->mtinst;
3350    return RISCV_EXCP_NONE;
3351}
3352
3353static RISCVException write_mtinst(CPURISCVState *env, int csrno,
3354                                   target_ulong val)
3355{
3356    env->mtinst = val;
3357    return RISCV_EXCP_NONE;
3358}
3359
3360/* Physical Memory Protection */
3361static RISCVException read_mseccfg(CPURISCVState *env, int csrno,
3362                                   target_ulong *val)
3363{
3364    *val = mseccfg_csr_read(env);
3365    return RISCV_EXCP_NONE;
3366}
3367
3368static RISCVException write_mseccfg(CPURISCVState *env, int csrno,
3369                                    target_ulong val)
3370{
3371    mseccfg_csr_write(env, val);
3372    return RISCV_EXCP_NONE;
3373}
3374
3375static RISCVException read_pmpcfg(CPURISCVState *env, int csrno,
3376                                  target_ulong *val)
3377{
3378    uint32_t reg_index = csrno - CSR_PMPCFG0;
3379
3380    *val = pmpcfg_csr_read(env, reg_index);
3381    return RISCV_EXCP_NONE;
3382}
3383
3384static RISCVException write_pmpcfg(CPURISCVState *env, int csrno,
3385                                   target_ulong val)
3386{
3387    uint32_t reg_index = csrno - CSR_PMPCFG0;
3388
3389    pmpcfg_csr_write(env, reg_index, val);
3390    return RISCV_EXCP_NONE;
3391}
3392
3393static RISCVException read_pmpaddr(CPURISCVState *env, int csrno,
3394                                   target_ulong *val)
3395{
3396    *val = pmpaddr_csr_read(env, csrno - CSR_PMPADDR0);
3397    return RISCV_EXCP_NONE;
3398}
3399
3400static RISCVException write_pmpaddr(CPURISCVState *env, int csrno,
3401                                    target_ulong val)
3402{
3403    pmpaddr_csr_write(env, csrno - CSR_PMPADDR0, val);
3404    return RISCV_EXCP_NONE;
3405}
3406
3407static RISCVException read_tselect(CPURISCVState *env, int csrno,
3408                                   target_ulong *val)
3409{
3410    *val = tselect_csr_read(env);
3411    return RISCV_EXCP_NONE;
3412}
3413
3414static RISCVException write_tselect(CPURISCVState *env, int csrno,
3415                                    target_ulong val)
3416{
3417    tselect_csr_write(env, val);
3418    return RISCV_EXCP_NONE;
3419}
3420
3421static RISCVException read_tdata(CPURISCVState *env, int csrno,
3422                                 target_ulong *val)
3423{
3424    /* return 0 in tdata1 to end the trigger enumeration */
3425    if (env->trigger_cur >= RV_MAX_TRIGGERS && csrno == CSR_TDATA1) {
3426        *val = 0;
3427        return RISCV_EXCP_NONE;
3428    }
3429
3430    if (!tdata_available(env, csrno - CSR_TDATA1)) {
3431        return RISCV_EXCP_ILLEGAL_INST;
3432    }
3433
3434    *val = tdata_csr_read(env, csrno - CSR_TDATA1);
3435    return RISCV_EXCP_NONE;
3436}
3437
3438static RISCVException write_tdata(CPURISCVState *env, int csrno,
3439                                  target_ulong val)
3440{
3441    if (!tdata_available(env, csrno - CSR_TDATA1)) {
3442        return RISCV_EXCP_ILLEGAL_INST;
3443    }
3444
3445    tdata_csr_write(env, csrno - CSR_TDATA1, val);
3446    return RISCV_EXCP_NONE;
3447}
3448
3449static RISCVException read_tinfo(CPURISCVState *env, int csrno,
3450                                 target_ulong *val)
3451{
3452    *val = tinfo_csr_read(env);
3453    return RISCV_EXCP_NONE;
3454}
3455
3456/*
3457 * Functions to access Pointer Masking feature registers
3458 * We have to check if current priv lvl could modify
3459 * csr in given mode
3460 */
3461static bool check_pm_current_disabled(CPURISCVState *env, int csrno)
3462{
3463    int csr_priv = get_field(csrno, 0x300);
3464    int pm_current;
3465
3466    if (env->debugger) {
3467        return false;
3468    }
3469    /*
3470     * If priv lvls differ that means we're accessing csr from higher priv lvl,
3471     * so allow the access
3472     */
3473    if (env->priv != csr_priv) {
3474        return false;
3475    }
3476    switch (env->priv) {
3477    case PRV_M:
3478        pm_current = get_field(env->mmte, M_PM_CURRENT);
3479        break;
3480    case PRV_S:
3481        pm_current = get_field(env->mmte, S_PM_CURRENT);
3482        break;
3483    case PRV_U:
3484        pm_current = get_field(env->mmte, U_PM_CURRENT);
3485        break;
3486    default:
3487        g_assert_not_reached();
3488    }
3489    /* It's same priv lvl, so we allow to modify csr only if pm.current==1 */
3490    return !pm_current;
3491}
3492
3493static RISCVException read_mmte(CPURISCVState *env, int csrno,
3494                                target_ulong *val)
3495{
3496    *val = env->mmte & MMTE_MASK;
3497    return RISCV_EXCP_NONE;
3498}
3499
3500static RISCVException write_mmte(CPURISCVState *env, int csrno,
3501                                 target_ulong val)
3502{
3503    uint64_t mstatus;
3504    target_ulong wpri_val = val & MMTE_MASK;
3505
3506    if (val != wpri_val) {
3507        qemu_log_mask(LOG_GUEST_ERROR, "%s" TARGET_FMT_lx " %s" TARGET_FMT_lx "\n",
3508                      "MMTE: WPRI violation written 0x", val,
3509                      "vs expected 0x", wpri_val);
3510    }
3511    /* for machine mode pm.current is hardwired to 1 */
3512    wpri_val |= MMTE_M_PM_CURRENT;
3513
3514    /* hardwiring pm.instruction bit to 0, since it's not supported yet */
3515    wpri_val &= ~(MMTE_M_PM_INSN | MMTE_S_PM_INSN | MMTE_U_PM_INSN);
3516    env->mmte = wpri_val | PM_EXT_DIRTY;
3517    riscv_cpu_update_mask(env);
3518
3519    /* Set XS and SD bits, since PM CSRs are dirty */
3520    mstatus = env->mstatus | MSTATUS_XS;
3521    write_mstatus(env, csrno, mstatus);
3522    return RISCV_EXCP_NONE;
3523}
3524
3525static RISCVException read_smte(CPURISCVState *env, int csrno,
3526                                target_ulong *val)
3527{
3528    *val = env->mmte & SMTE_MASK;
3529    return RISCV_EXCP_NONE;
3530}
3531
3532static RISCVException write_smte(CPURISCVState *env, int csrno,
3533                                 target_ulong val)
3534{
3535    target_ulong wpri_val = val & SMTE_MASK;
3536
3537    if (val != wpri_val) {
3538        qemu_log_mask(LOG_GUEST_ERROR, "%s" TARGET_FMT_lx " %s" TARGET_FMT_lx "\n",
3539                      "SMTE: WPRI violation written 0x", val,
3540                      "vs expected 0x", wpri_val);
3541    }
3542
3543    /* if pm.current==0 we can't modify current PM CSRs */
3544    if (check_pm_current_disabled(env, csrno)) {
3545        return RISCV_EXCP_NONE;
3546    }
3547
3548    wpri_val |= (env->mmte & ~SMTE_MASK);
3549    write_mmte(env, csrno, wpri_val);
3550    return RISCV_EXCP_NONE;
3551}
3552
3553static RISCVException read_umte(CPURISCVState *env, int csrno,
3554                                target_ulong *val)
3555{
3556    *val = env->mmte & UMTE_MASK;
3557    return RISCV_EXCP_NONE;
3558}
3559
3560static RISCVException write_umte(CPURISCVState *env, int csrno,
3561                                 target_ulong val)
3562{
3563    target_ulong wpri_val = val & UMTE_MASK;
3564
3565    if (val != wpri_val) {
3566        qemu_log_mask(LOG_GUEST_ERROR, "%s" TARGET_FMT_lx " %s" TARGET_FMT_lx "\n",
3567                      "UMTE: WPRI violation written 0x", val,
3568                      "vs expected 0x", wpri_val);
3569    }
3570
3571    if (check_pm_current_disabled(env, csrno)) {
3572        return RISCV_EXCP_NONE;
3573    }
3574
3575    wpri_val |= (env->mmte & ~UMTE_MASK);
3576    write_mmte(env, csrno, wpri_val);
3577    return RISCV_EXCP_NONE;
3578}
3579
3580static RISCVException read_mpmmask(CPURISCVState *env, int csrno,
3581                                   target_ulong *val)
3582{
3583    *val = env->mpmmask;
3584    return RISCV_EXCP_NONE;
3585}
3586
3587static RISCVException write_mpmmask(CPURISCVState *env, int csrno,
3588                                    target_ulong val)
3589{
3590    uint64_t mstatus;
3591
3592    env->mpmmask = val;
3593    if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
3594        env->cur_pmmask = val;
3595    }
3596    env->mmte |= PM_EXT_DIRTY;
3597
3598    /* Set XS and SD bits, since PM CSRs are dirty */
3599    mstatus = env->mstatus | MSTATUS_XS;
3600    write_mstatus(env, csrno, mstatus);
3601    return RISCV_EXCP_NONE;
3602}
3603
3604static RISCVException read_spmmask(CPURISCVState *env, int csrno,
3605                                   target_ulong *val)
3606{
3607    *val = env->spmmask;
3608    return RISCV_EXCP_NONE;
3609}
3610
3611static RISCVException write_spmmask(CPURISCVState *env, int csrno,
3612                                    target_ulong val)
3613{
3614    uint64_t mstatus;
3615
3616    /* if pm.current==0 we can't modify current PM CSRs */
3617    if (check_pm_current_disabled(env, csrno)) {
3618        return RISCV_EXCP_NONE;
3619    }
3620    env->spmmask = val;
3621    if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
3622        env->cur_pmmask = val;
3623    }
3624    env->mmte |= PM_EXT_DIRTY;
3625
3626    /* Set XS and SD bits, since PM CSRs are dirty */
3627    mstatus = env->mstatus | MSTATUS_XS;
3628    write_mstatus(env, csrno, mstatus);
3629    return RISCV_EXCP_NONE;
3630}
3631
3632static RISCVException read_upmmask(CPURISCVState *env, int csrno,
3633                                   target_ulong *val)
3634{
3635    *val = env->upmmask;
3636    return RISCV_EXCP_NONE;
3637}
3638
3639static RISCVException write_upmmask(CPURISCVState *env, int csrno,
3640                                    target_ulong val)
3641{
3642    uint64_t mstatus;
3643
3644    /* if pm.current==0 we can't modify current PM CSRs */
3645    if (check_pm_current_disabled(env, csrno)) {
3646        return RISCV_EXCP_NONE;
3647    }
3648    env->upmmask = val;
3649    if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
3650        env->cur_pmmask = val;
3651    }
3652    env->mmte |= PM_EXT_DIRTY;
3653
3654    /* Set XS and SD bits, since PM CSRs are dirty */
3655    mstatus = env->mstatus | MSTATUS_XS;
3656    write_mstatus(env, csrno, mstatus);
3657    return RISCV_EXCP_NONE;
3658}
3659
3660static RISCVException read_mpmbase(CPURISCVState *env, int csrno,
3661                                   target_ulong *val)
3662{
3663    *val = env->mpmbase;
3664    return RISCV_EXCP_NONE;
3665}
3666
3667static RISCVException write_mpmbase(CPURISCVState *env, int csrno,
3668                                    target_ulong val)
3669{
3670    uint64_t mstatus;
3671
3672    env->mpmbase = val;
3673    if ((env->priv == PRV_M) && (env->mmte & M_PM_ENABLE)) {
3674        env->cur_pmbase = val;
3675    }
3676    env->mmte |= PM_EXT_DIRTY;
3677
3678    /* Set XS and SD bits, since PM CSRs are dirty */
3679    mstatus = env->mstatus | MSTATUS_XS;
3680    write_mstatus(env, csrno, mstatus);
3681    return RISCV_EXCP_NONE;
3682}
3683
3684static RISCVException read_spmbase(CPURISCVState *env, int csrno,
3685                                   target_ulong *val)
3686{
3687    *val = env->spmbase;
3688    return RISCV_EXCP_NONE;
3689}
3690
3691static RISCVException write_spmbase(CPURISCVState *env, int csrno,
3692                                    target_ulong val)
3693{
3694    uint64_t mstatus;
3695
3696    /* if pm.current==0 we can't modify current PM CSRs */
3697    if (check_pm_current_disabled(env, csrno)) {
3698        return RISCV_EXCP_NONE;
3699    }
3700    env->spmbase = val;
3701    if ((env->priv == PRV_S) && (env->mmte & S_PM_ENABLE)) {
3702        env->cur_pmbase = val;
3703    }
3704    env->mmte |= PM_EXT_DIRTY;
3705
3706    /* Set XS and SD bits, since PM CSRs are dirty */
3707    mstatus = env->mstatus | MSTATUS_XS;
3708    write_mstatus(env, csrno, mstatus);
3709    return RISCV_EXCP_NONE;
3710}
3711
3712static RISCVException read_upmbase(CPURISCVState *env, int csrno,
3713                                   target_ulong *val)
3714{
3715    *val = env->upmbase;
3716    return RISCV_EXCP_NONE;
3717}
3718
3719static RISCVException write_upmbase(CPURISCVState *env, int csrno,
3720                                    target_ulong val)
3721{
3722    uint64_t mstatus;
3723
3724    /* if pm.current==0 we can't modify current PM CSRs */
3725    if (check_pm_current_disabled(env, csrno)) {
3726        return RISCV_EXCP_NONE;
3727    }
3728    env->upmbase = val;
3729    if ((env->priv == PRV_U) && (env->mmte & U_PM_ENABLE)) {
3730        env->cur_pmbase = val;
3731    }
3732    env->mmte |= PM_EXT_DIRTY;
3733
3734    /* Set XS and SD bits, since PM CSRs are dirty */
3735    mstatus = env->mstatus | MSTATUS_XS;
3736    write_mstatus(env, csrno, mstatus);
3737    return RISCV_EXCP_NONE;
3738}
3739
3740#endif
3741
3742/* Crypto Extension */
3743static RISCVException rmw_seed(CPURISCVState *env, int csrno,
3744                               target_ulong *ret_value,
3745                               target_ulong new_value,
3746                               target_ulong write_mask)
3747{
3748    uint16_t random_v;
3749    Error *random_e = NULL;
3750    int random_r;
3751    target_ulong rval;
3752
3753    random_r = qemu_guest_getrandom(&random_v, 2, &random_e);
3754    if (unlikely(random_r < 0)) {
3755        /*
3756         * Failed, for unknown reasons in the crypto subsystem.
3757         * The best we can do is log the reason and return a
3758         * failure indication to the guest.  There is no reason
3759         * we know to expect the failure to be transitory, so
3760         * indicate DEAD to avoid having the guest spin on WAIT.
3761         */
3762        qemu_log_mask(LOG_UNIMP, "%s: Crypto failure: %s",
3763                      __func__, error_get_pretty(random_e));
3764        error_free(random_e);
3765        rval = SEED_OPST_DEAD;
3766    } else {
3767        rval = random_v | SEED_OPST_ES16;
3768    }
3769
3770    if (ret_value) {
3771        *ret_value = rval;
3772    }
3773
3774    return RISCV_EXCP_NONE;
3775}
3776
3777/*
3778 * riscv_csrrw - read and/or update control and status register
3779 *
3780 * csrr   <->  riscv_csrrw(env, csrno, ret_value, 0, 0);
3781 * csrrw  <->  riscv_csrrw(env, csrno, ret_value, value, -1);
3782 * csrrs  <->  riscv_csrrw(env, csrno, ret_value, -1, value);
3783 * csrrc  <->  riscv_csrrw(env, csrno, ret_value, 0, value);
3784 */
3785
3786static inline RISCVException riscv_csrrw_check(CPURISCVState *env,
3787                                               int csrno,
3788                                               bool write_mask,
3789                                               RISCVCPU *cpu)
3790{
3791    /* check privileges and return RISCV_EXCP_ILLEGAL_INST if check fails */
3792    bool read_only = get_field(csrno, 0xC00) == 3;
3793    int csr_min_priv = csr_ops[csrno].min_priv_ver;
3794
3795    /* ensure the CSR extension is enabled */
3796    if (!cpu->cfg.ext_icsr) {
3797        return RISCV_EXCP_ILLEGAL_INST;
3798    }
3799
3800    /* ensure CSR is implemented by checking predicate */
3801    if (!csr_ops[csrno].predicate) {
3802        return RISCV_EXCP_ILLEGAL_INST;
3803    }
3804
3805    /* privileged spec version check */
3806    if (env->priv_ver < csr_min_priv) {
3807        return RISCV_EXCP_ILLEGAL_INST;
3808    }
3809
3810    /* read / write check */
3811    if (write_mask && read_only) {
3812        return RISCV_EXCP_ILLEGAL_INST;
3813    }
3814
3815    /*
3816     * The predicate() not only does existence check but also does some
3817     * access control check which triggers for example virtual instruction
3818     * exception in some cases. When writing read-only CSRs in those cases
3819     * illegal instruction exception should be triggered instead of virtual
3820     * instruction exception. Hence this comes after the read / write check.
3821     */
3822    RISCVException ret = csr_ops[csrno].predicate(env, csrno);
3823    if (ret != RISCV_EXCP_NONE) {
3824        return ret;
3825    }
3826
3827#if !defined(CONFIG_USER_ONLY)
3828    int csr_priv, effective_priv = env->priv;
3829
3830    if (riscv_has_ext(env, RVH) && env->priv == PRV_S &&
3831        !riscv_cpu_virt_enabled(env)) {
3832        /*
3833         * We are in HS mode. Add 1 to the effective privledge level to
3834         * allow us to access the Hypervisor CSRs.
3835         */
3836        effective_priv++;
3837    }
3838
3839    csr_priv = get_field(csrno, 0x300);
3840    if (!env->debugger && (effective_priv < csr_priv)) {
3841        if (csr_priv == (PRV_S + 1) && riscv_cpu_virt_enabled(env)) {
3842            return RISCV_EXCP_VIRT_INSTRUCTION_FAULT;
3843        }
3844        return RISCV_EXCP_ILLEGAL_INST;
3845    }
3846#endif
3847    return RISCV_EXCP_NONE;
3848}
3849
3850static RISCVException riscv_csrrw_do64(CPURISCVState *env, int csrno,
3851                                       target_ulong *ret_value,
3852                                       target_ulong new_value,
3853                                       target_ulong write_mask)
3854{
3855    RISCVException ret;
3856    target_ulong old_value;
3857
3858    /* execute combined read/write operation if it exists */
3859    if (csr_ops[csrno].op) {
3860        return csr_ops[csrno].op(env, csrno, ret_value, new_value, write_mask);
3861    }
3862
3863    /* if no accessor exists then return failure */
3864    if (!csr_ops[csrno].read) {
3865        return RISCV_EXCP_ILLEGAL_INST;
3866    }
3867    /* read old value */
3868    ret = csr_ops[csrno].read(env, csrno, &old_value);
3869    if (ret != RISCV_EXCP_NONE) {
3870        return ret;
3871    }
3872
3873    /* write value if writable and write mask set, otherwise drop writes */
3874    if (write_mask) {
3875        new_value = (old_value & ~write_mask) | (new_value & write_mask);
3876        if (csr_ops[csrno].write) {
3877            ret = csr_ops[csrno].write(env, csrno, new_value);
3878            if (ret != RISCV_EXCP_NONE) {
3879                return ret;
3880            }
3881        }
3882    }
3883
3884    /* return old value */
3885    if (ret_value) {
3886        *ret_value = old_value;
3887    }
3888
3889    return RISCV_EXCP_NONE;
3890}
3891
3892RISCVException riscv_csrrw(CPURISCVState *env, int csrno,
3893                           target_ulong *ret_value,
3894                           target_ulong new_value, target_ulong write_mask)
3895{
3896    RISCVCPU *cpu = env_archcpu(env);
3897
3898    RISCVException ret = riscv_csrrw_check(env, csrno, write_mask, cpu);
3899    if (ret != RISCV_EXCP_NONE) {
3900        return ret;
3901    }
3902
3903    return riscv_csrrw_do64(env, csrno, ret_value, new_value, write_mask);
3904}
3905
3906static RISCVException riscv_csrrw_do128(CPURISCVState *env, int csrno,
3907                                        Int128 *ret_value,
3908                                        Int128 new_value,
3909                                        Int128 write_mask)
3910{
3911    RISCVException ret;
3912    Int128 old_value;
3913
3914    /* read old value */
3915    ret = csr_ops[csrno].read128(env, csrno, &old_value);
3916    if (ret != RISCV_EXCP_NONE) {
3917        return ret;
3918    }
3919
3920    /* write value if writable and write mask set, otherwise drop writes */
3921    if (int128_nz(write_mask)) {
3922        new_value = int128_or(int128_and(old_value, int128_not(write_mask)),
3923                              int128_and(new_value, write_mask));
3924        if (csr_ops[csrno].write128) {
3925            ret = csr_ops[csrno].write128(env, csrno, new_value);
3926            if (ret != RISCV_EXCP_NONE) {
3927                return ret;
3928            }
3929        } else if (csr_ops[csrno].write) {
3930            /* avoids having to write wrappers for all registers */
3931            ret = csr_ops[csrno].write(env, csrno, int128_getlo(new_value));
3932            if (ret != RISCV_EXCP_NONE) {
3933                return ret;
3934            }
3935        }
3936    }
3937
3938    /* return old value */
3939    if (ret_value) {
3940        *ret_value = old_value;
3941    }
3942
3943    return RISCV_EXCP_NONE;
3944}
3945
3946RISCVException riscv_csrrw_i128(CPURISCVState *env, int csrno,
3947                                Int128 *ret_value,
3948                                Int128 new_value, Int128 write_mask)
3949{
3950    RISCVException ret;
3951    RISCVCPU *cpu = env_archcpu(env);
3952
3953    ret = riscv_csrrw_check(env, csrno, int128_nz(write_mask), cpu);
3954    if (ret != RISCV_EXCP_NONE) {
3955        return ret;
3956    }
3957
3958    if (csr_ops[csrno].read128) {
3959        return riscv_csrrw_do128(env, csrno, ret_value, new_value, write_mask);
3960    }
3961
3962    /*
3963     * Fall back to 64-bit version for now, if the 128-bit alternative isn't
3964     * at all defined.
3965     * Note, some CSRs don't need to extend to MXLEN (64 upper bits non
3966     * significant), for those, this fallback is correctly handling the accesses
3967     */
3968    target_ulong old_value;
3969    ret = riscv_csrrw_do64(env, csrno, &old_value,
3970                           int128_getlo(new_value),
3971                           int128_getlo(write_mask));
3972    if (ret == RISCV_EXCP_NONE && ret_value) {
3973        *ret_value = int128_make64(old_value);
3974    }
3975    return ret;
3976}
3977
3978/*
3979 * Debugger support.  If not in user mode, set env->debugger before the
3980 * riscv_csrrw call and clear it after the call.
3981 */
3982RISCVException riscv_csrrw_debug(CPURISCVState *env, int csrno,
3983                                 target_ulong *ret_value,
3984                                 target_ulong new_value,
3985                                 target_ulong write_mask)
3986{
3987    RISCVException ret;
3988#if !defined(CONFIG_USER_ONLY)
3989    env->debugger = true;
3990#endif
3991    ret = riscv_csrrw(env, csrno, ret_value, new_value, write_mask);
3992#if !defined(CONFIG_USER_ONLY)
3993    env->debugger = false;
3994#endif
3995    return ret;
3996}
3997
3998/*
3999 * Control and Status Register function table
4000 * riscv_csr_operations::predicate() must be provided for an implemented CSR
4001 */
4002riscv_csr_operations csr_ops[CSR_TABLE_SIZE] = {
4003    /* User Floating-Point CSRs */
4004    [CSR_FFLAGS]   = { "fflags",   fs,     read_fflags,  write_fflags },
4005    [CSR_FRM]      = { "frm",      fs,     read_frm,     write_frm    },
4006    [CSR_FCSR]     = { "fcsr",     fs,     read_fcsr,    write_fcsr   },
4007    /* Vector CSRs */
4008    [CSR_VSTART]   = { "vstart",   vs,     read_vstart,  write_vstart },
4009    [CSR_VXSAT]    = { "vxsat",    vs,     read_vxsat,   write_vxsat  },
4010    [CSR_VXRM]     = { "vxrm",     vs,     read_vxrm,    write_vxrm   },
4011    [CSR_VCSR]     = { "vcsr",     vs,     read_vcsr,    write_vcsr   },
4012    [CSR_VL]       = { "vl",       vs,     read_vl                    },
4013    [CSR_VTYPE]    = { "vtype",    vs,     read_vtype                 },
4014    [CSR_VLENB]    = { "vlenb",    vs,     read_vlenb                 },
4015    /* User Timers and Counters */
4016    [CSR_CYCLE]    = { "cycle",    ctr,    read_hpmcounter  },
4017    [CSR_INSTRET]  = { "instret",  ctr,    read_hpmcounter  },
4018    [CSR_CYCLEH]   = { "cycleh",   ctr32,  read_hpmcounterh },
4019    [CSR_INSTRETH] = { "instreth", ctr32,  read_hpmcounterh },
4020
4021    /*
4022     * In privileged mode, the monitor will have to emulate TIME CSRs only if
4023     * rdtime callback is not provided by machine/platform emulation.
4024     */
4025    [CSR_TIME]  = { "time",  ctr,   read_time  },
4026    [CSR_TIMEH] = { "timeh", ctr32, read_timeh },
4027
4028    /* Crypto Extension */
4029    [CSR_SEED] = { "seed", seed, NULL, NULL, rmw_seed },
4030
4031#if !defined(CONFIG_USER_ONLY)
4032    /* Machine Timers and Counters */
4033    [CSR_MCYCLE]    = { "mcycle",    any,   read_hpmcounter,
4034                        write_mhpmcounter                    },
4035    [CSR_MINSTRET]  = { "minstret",  any,   read_hpmcounter,
4036                        write_mhpmcounter                    },
4037    [CSR_MCYCLEH]   = { "mcycleh",   any32, read_hpmcounterh,
4038                        write_mhpmcounterh                   },
4039    [CSR_MINSTRETH] = { "minstreth", any32, read_hpmcounterh,
4040                        write_mhpmcounterh                   },
4041
4042    /* Machine Information Registers */
4043    [CSR_MVENDORID] = { "mvendorid", any,   read_mvendorid },
4044    [CSR_MARCHID]   = { "marchid",   any,   read_marchid   },
4045    [CSR_MIMPID]    = { "mimpid",    any,   read_mimpid    },
4046    [CSR_MHARTID]   = { "mhartid",   any,   read_mhartid   },
4047
4048    [CSR_MCONFIGPTR]  = { "mconfigptr", any,   read_zero,
4049                          .min_priv_ver = PRIV_VERSION_1_12_0 },
4050    /* Machine Trap Setup */
4051    [CSR_MSTATUS]     = { "mstatus",    any,   read_mstatus, write_mstatus,
4052                          NULL,                read_mstatus_i128           },
4053    [CSR_MISA]        = { "misa",       any,   read_misa,    write_misa,
4054                          NULL,                read_misa_i128              },
4055    [CSR_MIDELEG]     = { "mideleg",    any,   NULL, NULL,   rmw_mideleg   },
4056    [CSR_MEDELEG]     = { "medeleg",    any,   read_medeleg, write_medeleg },
4057    [CSR_MIE]         = { "mie",        any,   NULL, NULL,   rmw_mie       },
4058    [CSR_MTVEC]       = { "mtvec",      any,   read_mtvec,   write_mtvec   },
4059    [CSR_MCOUNTEREN]  = { "mcounteren", umode, read_mcounteren,
4060                          write_mcounteren                                 },
4061
4062    [CSR_MSTATUSH]    = { "mstatush",   any32, read_mstatush,
4063                          write_mstatush                                   },
4064
4065    /* Machine Trap Handling */
4066    [CSR_MSCRATCH] = { "mscratch", any,  read_mscratch, write_mscratch,
4067                       NULL, read_mscratch_i128, write_mscratch_i128   },
4068    [CSR_MEPC]     = { "mepc",     any,  read_mepc,     write_mepc     },
4069    [CSR_MCAUSE]   = { "mcause",   any,  read_mcause,   write_mcause   },
4070    [CSR_MTVAL]    = { "mtval",    any,  read_mtval,    write_mtval    },
4071    [CSR_MIP]      = { "mip",      any,  NULL,    NULL, rmw_mip        },
4072
4073    /* Machine-Level Window to Indirectly Accessed Registers (AIA) */
4074    [CSR_MISELECT] = { "miselect", aia_any,   NULL, NULL,    rmw_xiselect },
4075    [CSR_MIREG]    = { "mireg",    aia_any,   NULL, NULL,    rmw_xireg },
4076
4077    /* Machine-Level Interrupts (AIA) */
4078    [CSR_MTOPEI]   = { "mtopei",   aia_any, NULL, NULL, rmw_xtopei },
4079    [CSR_MTOPI]    = { "mtopi",    aia_any, read_mtopi },
4080
4081    /* Virtual Interrupts for Supervisor Level (AIA) */
4082    [CSR_MVIEN]    = { "mvien",    aia_any, read_zero, write_ignore },
4083    [CSR_MVIP]     = { "mvip",     aia_any, read_zero, write_ignore },
4084
4085    /* Machine-Level High-Half CSRs (AIA) */
4086    [CSR_MIDELEGH] = { "midelegh", aia_any32, NULL, NULL, rmw_midelegh },
4087    [CSR_MIEH]     = { "mieh",     aia_any32, NULL, NULL, rmw_mieh     },
4088    [CSR_MVIENH]   = { "mvienh",   aia_any32, read_zero,  write_ignore },
4089    [CSR_MVIPH]    = { "mviph",    aia_any32, read_zero,  write_ignore },
4090    [CSR_MIPH]     = { "miph",     aia_any32, NULL, NULL, rmw_miph     },
4091
4092    /* Execution environment configuration */
4093    [CSR_MENVCFG]  = { "menvcfg",  umode, read_menvcfg,  write_menvcfg,
4094                       .min_priv_ver = PRIV_VERSION_1_12_0              },
4095    [CSR_MENVCFGH] = { "menvcfgh", umode32, read_menvcfgh, write_menvcfgh,
4096                       .min_priv_ver = PRIV_VERSION_1_12_0              },
4097    [CSR_SENVCFG]  = { "senvcfg",  smode, read_senvcfg,  write_senvcfg,
4098                       .min_priv_ver = PRIV_VERSION_1_12_0              },
4099    [CSR_HENVCFG]  = { "henvcfg",  hmode, read_henvcfg, write_henvcfg,
4100                       .min_priv_ver = PRIV_VERSION_1_12_0              },
4101    [CSR_HENVCFGH] = { "henvcfgh", hmode32, read_henvcfgh, write_henvcfgh,
4102                       .min_priv_ver = PRIV_VERSION_1_12_0              },
4103
4104    /* Smstateen extension CSRs */
4105    [CSR_MSTATEEN0] = { "mstateen0", mstateen, read_mstateen, write_mstateen0,
4106                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4107    [CSR_MSTATEEN0H] = { "mstateen0h", mstateen, read_mstateenh,
4108                          write_mstateen0h,
4109                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4110    [CSR_MSTATEEN1] = { "mstateen1", mstateen, read_mstateen,
4111                        write_mstateen_1_3,
4112                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4113    [CSR_MSTATEEN1H] = { "mstateen1h", mstateen, read_mstateenh,
4114                         write_mstateenh_1_3,
4115                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4116    [CSR_MSTATEEN2] = { "mstateen2", mstateen, read_mstateen,
4117                        write_mstateen_1_3,
4118                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4119    [CSR_MSTATEEN2H] = { "mstateen2h", mstateen, read_mstateenh,
4120                         write_mstateenh_1_3,
4121                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4122    [CSR_MSTATEEN3] = { "mstateen3", mstateen, read_mstateen,
4123                        write_mstateen_1_3,
4124                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4125    [CSR_MSTATEEN3H] = { "mstateen3h", mstateen, read_mstateenh,
4126                         write_mstateenh_1_3,
4127                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4128    [CSR_HSTATEEN0] = { "hstateen0", hstateen, read_hstateen, write_hstateen0,
4129                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4130    [CSR_HSTATEEN0H] = { "hstateen0h", hstateenh, read_hstateenh,
4131                         write_hstateen0h,
4132                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4133    [CSR_HSTATEEN1] = { "hstateen1", hstateen, read_hstateen,
4134                        write_hstateen_1_3,
4135                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4136    [CSR_HSTATEEN1H] = { "hstateen1h", hstateenh, read_hstateenh,
4137                         write_hstateenh_1_3,
4138                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4139    [CSR_HSTATEEN2] = { "hstateen2", hstateen, read_hstateen,
4140                        write_hstateen_1_3,
4141                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4142    [CSR_HSTATEEN2H] = { "hstateen2h", hstateenh, read_hstateenh,
4143                         write_hstateenh_1_3,
4144                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4145    [CSR_HSTATEEN3] = { "hstateen3", hstateen, read_hstateen,
4146                        write_hstateen_1_3,
4147                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4148    [CSR_HSTATEEN3H] = { "hstateen3h", hstateenh, read_hstateenh,
4149                         write_hstateenh_1_3,
4150                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4151    [CSR_SSTATEEN0] = { "sstateen0", sstateen, read_sstateen, write_sstateen0,
4152                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4153    [CSR_SSTATEEN1] = { "sstateen1", sstateen, read_sstateen,
4154                        write_sstateen_1_3,
4155                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4156    [CSR_SSTATEEN2] = { "sstateen2", sstateen, read_sstateen,
4157                        write_sstateen_1_3,
4158                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4159    [CSR_SSTATEEN3] = { "sstateen3", sstateen, read_sstateen,
4160                        write_sstateen_1_3,
4161                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4162
4163    /* Supervisor Trap Setup */
4164    [CSR_SSTATUS]    = { "sstatus",    smode, read_sstatus,    write_sstatus,
4165                         NULL,                read_sstatus_i128               },
4166    [CSR_SIE]        = { "sie",        smode, NULL,   NULL,    rmw_sie        },
4167    [CSR_STVEC]      = { "stvec",      smode, read_stvec,      write_stvec    },
4168    [CSR_SCOUNTEREN] = { "scounteren", smode, read_scounteren,
4169                         write_scounteren                                     },
4170
4171    /* Supervisor Trap Handling */
4172    [CSR_SSCRATCH] = { "sscratch", smode, read_sscratch, write_sscratch,
4173                       NULL, read_sscratch_i128, write_sscratch_i128    },
4174    [CSR_SEPC]     = { "sepc",     smode, read_sepc,     write_sepc     },
4175    [CSR_SCAUSE]   = { "scause",   smode, read_scause,   write_scause   },
4176    [CSR_STVAL]    = { "stval",    smode, read_stval,    write_stval    },
4177    [CSR_SIP]      = { "sip",      smode, NULL,    NULL, rmw_sip        },
4178    [CSR_STIMECMP] = { "stimecmp", sstc, read_stimecmp, write_stimecmp,
4179                       .min_priv_ver = PRIV_VERSION_1_12_0 },
4180    [CSR_STIMECMPH] = { "stimecmph", sstc_32, read_stimecmph, write_stimecmph,
4181                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4182    [CSR_VSTIMECMP] = { "vstimecmp", sstc, read_vstimecmp,
4183                        write_vstimecmp,
4184                        .min_priv_ver = PRIV_VERSION_1_12_0 },
4185    [CSR_VSTIMECMPH] = { "vstimecmph", sstc_32, read_vstimecmph,
4186                         write_vstimecmph,
4187                         .min_priv_ver = PRIV_VERSION_1_12_0 },
4188
4189    /* Supervisor Protection and Translation */
4190    [CSR_SATP]     = { "satp",     smode, read_satp,     write_satp     },
4191
4192    /* Supervisor-Level Window to Indirectly Accessed Registers (AIA) */
4193    [CSR_SISELECT]   = { "siselect",   aia_smode, NULL, NULL, rmw_xiselect },
4194    [CSR_SIREG]      = { "sireg",      aia_smode, NULL, NULL, rmw_xireg },
4195
4196    /* Supervisor-Level Interrupts (AIA) */
4197    [CSR_STOPEI]     = { "stopei",     aia_smode, NULL, NULL, rmw_xtopei },
4198    [CSR_STOPI]      = { "stopi",      aia_smode, read_stopi },
4199
4200    /* Supervisor-Level High-Half CSRs (AIA) */
4201    [CSR_SIEH]       = { "sieh",   aia_smode32, NULL, NULL, rmw_sieh },
4202    [CSR_SIPH]       = { "siph",   aia_smode32, NULL, NULL, rmw_siph },
4203
4204    [CSR_HSTATUS]     = { "hstatus",     hmode,   read_hstatus, write_hstatus,
4205                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4206    [CSR_HEDELEG]     = { "hedeleg",     hmode,   read_hedeleg, write_hedeleg,
4207                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4208    [CSR_HIDELEG]     = { "hideleg",     hmode,   NULL,   NULL, rmw_hideleg,
4209                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4210    [CSR_HVIP]        = { "hvip",        hmode,   NULL,   NULL, rmw_hvip,
4211                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4212    [CSR_HIP]         = { "hip",         hmode,   NULL,   NULL, rmw_hip,
4213                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4214    [CSR_HIE]         = { "hie",         hmode,   NULL,   NULL, rmw_hie,
4215                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4216    [CSR_HCOUNTEREN]  = { "hcounteren",  hmode,   read_hcounteren,
4217                          write_hcounteren,
4218                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4219    [CSR_HGEIE]       = { "hgeie",       hmode,   read_hgeie,   write_hgeie,
4220                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4221    [CSR_HTVAL]       = { "htval",       hmode,   read_htval,   write_htval,
4222                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4223    [CSR_HTINST]      = { "htinst",      hmode,   read_htinst,  write_htinst,
4224                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4225    [CSR_HGEIP]       = { "hgeip",       hmode,   read_hgeip,
4226                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4227    [CSR_HGATP]       = { "hgatp",       hmode,   read_hgatp,   write_hgatp,
4228                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4229    [CSR_HTIMEDELTA]  = { "htimedelta",  hmode,   read_htimedelta,
4230                          write_htimedelta,
4231                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4232    [CSR_HTIMEDELTAH] = { "htimedeltah", hmode32, read_htimedeltah,
4233                          write_htimedeltah,
4234                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4235
4236    [CSR_VSSTATUS]    = { "vsstatus",    hmode,   read_vsstatus,
4237                          write_vsstatus,
4238                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4239    [CSR_VSIP]        = { "vsip",        hmode,   NULL,    NULL, rmw_vsip,
4240                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4241    [CSR_VSIE]        = { "vsie",        hmode,   NULL,    NULL, rmw_vsie ,
4242                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4243    [CSR_VSTVEC]      = { "vstvec",      hmode,   read_vstvec,   write_vstvec,
4244                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4245    [CSR_VSSCRATCH]   = { "vsscratch",   hmode,   read_vsscratch,
4246                          write_vsscratch,
4247                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4248    [CSR_VSEPC]       = { "vsepc",       hmode,   read_vsepc,    write_vsepc,
4249                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4250    [CSR_VSCAUSE]     = { "vscause",     hmode,   read_vscause,  write_vscause,
4251                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4252    [CSR_VSTVAL]      = { "vstval",      hmode,   read_vstval,   write_vstval,
4253                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4254    [CSR_VSATP]       = { "vsatp",       hmode,   read_vsatp,    write_vsatp,
4255                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4256
4257    [CSR_MTVAL2]      = { "mtval2",      hmode,   read_mtval2,   write_mtval2,
4258                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4259    [CSR_MTINST]      = { "mtinst",      hmode,   read_mtinst,   write_mtinst,
4260                          .min_priv_ver = PRIV_VERSION_1_12_0                },
4261
4262    /* Virtual Interrupts and Interrupt Priorities (H-extension with AIA) */
4263    [CSR_HVIEN]       = { "hvien",       aia_hmode, read_zero, write_ignore },
4264    [CSR_HVICTL]      = { "hvictl",      aia_hmode, read_hvictl,
4265                          write_hvictl                                      },
4266    [CSR_HVIPRIO1]    = { "hviprio1",    aia_hmode, read_hviprio1,
4267                          write_hviprio1                                    },
4268    [CSR_HVIPRIO2]    = { "hviprio2",    aia_hmode, read_hviprio2,
4269                          write_hviprio2                                    },
4270
4271    /*
4272     * VS-Level Window to Indirectly Accessed Registers (H-extension with AIA)
4273     */
4274    [CSR_VSISELECT]   = { "vsiselect",   aia_hmode, NULL, NULL,
4275                          rmw_xiselect                                     },
4276    [CSR_VSIREG]      = { "vsireg",      aia_hmode, NULL, NULL, rmw_xireg  },
4277
4278    /* VS-Level Interrupts (H-extension with AIA) */
4279    [CSR_VSTOPEI]     = { "vstopei",     aia_hmode, NULL, NULL, rmw_xtopei },
4280    [CSR_VSTOPI]      = { "vstopi",      aia_hmode, read_vstopi },
4281
4282    /* Hypervisor and VS-Level High-Half CSRs (H-extension with AIA) */
4283    [CSR_HIDELEGH]    = { "hidelegh",    aia_hmode32, NULL, NULL,
4284                          rmw_hidelegh                                      },
4285    [CSR_HVIENH]      = { "hvienh",      aia_hmode32, read_zero,
4286                          write_ignore                                      },
4287    [CSR_HVIPH]       = { "hviph",       aia_hmode32, NULL, NULL, rmw_hviph },
4288    [CSR_HVIPRIO1H]   = { "hviprio1h",   aia_hmode32, read_hviprio1h,
4289                          write_hviprio1h                                   },
4290    [CSR_HVIPRIO2H]   = { "hviprio2h",   aia_hmode32, read_hviprio2h,
4291                          write_hviprio2h                                   },
4292    [CSR_VSIEH]       = { "vsieh",       aia_hmode32, NULL, NULL, rmw_vsieh },
4293    [CSR_VSIPH]       = { "vsiph",       aia_hmode32, NULL, NULL, rmw_vsiph },
4294
4295    /* Physical Memory Protection */
4296    [CSR_MSECCFG]    = { "mseccfg",  epmp, read_mseccfg, write_mseccfg,
4297                         .min_priv_ver = PRIV_VERSION_1_11_0           },
4298    [CSR_PMPCFG0]    = { "pmpcfg0",   pmp, read_pmpcfg,  write_pmpcfg  },
4299    [CSR_PMPCFG1]    = { "pmpcfg1",   pmp, read_pmpcfg,  write_pmpcfg  },
4300    [CSR_PMPCFG2]    = { "pmpcfg2",   pmp, read_pmpcfg,  write_pmpcfg  },
4301    [CSR_PMPCFG3]    = { "pmpcfg3",   pmp, read_pmpcfg,  write_pmpcfg  },
4302    [CSR_PMPADDR0]   = { "pmpaddr0",  pmp, read_pmpaddr, write_pmpaddr },
4303    [CSR_PMPADDR1]   = { "pmpaddr1",  pmp, read_pmpaddr, write_pmpaddr },
4304    [CSR_PMPADDR2]   = { "pmpaddr2",  pmp, read_pmpaddr, write_pmpaddr },
4305    [CSR_PMPADDR3]   = { "pmpaddr3",  pmp, read_pmpaddr, write_pmpaddr },
4306    [CSR_PMPADDR4]   = { "pmpaddr4",  pmp, read_pmpaddr, write_pmpaddr },
4307    [CSR_PMPADDR5]   = { "pmpaddr5",  pmp, read_pmpaddr, write_pmpaddr },
4308    [CSR_PMPADDR6]   = { "pmpaddr6",  pmp, read_pmpaddr, write_pmpaddr },
4309    [CSR_PMPADDR7]   = { "pmpaddr7",  pmp, read_pmpaddr, write_pmpaddr },
4310    [CSR_PMPADDR8]   = { "pmpaddr8",  pmp, read_pmpaddr, write_pmpaddr },
4311    [CSR_PMPADDR9]   = { "pmpaddr9",  pmp, read_pmpaddr, write_pmpaddr },
4312    [CSR_PMPADDR10]  = { "pmpaddr10", pmp, read_pmpaddr, write_pmpaddr },
4313    [CSR_PMPADDR11]  = { "pmpaddr11", pmp, read_pmpaddr, write_pmpaddr },
4314    [CSR_PMPADDR12]  = { "pmpaddr12", pmp, read_pmpaddr, write_pmpaddr },
4315    [CSR_PMPADDR13]  = { "pmpaddr13", pmp, read_pmpaddr, write_pmpaddr },
4316    [CSR_PMPADDR14] =  { "pmpaddr14", pmp, read_pmpaddr, write_pmpaddr },
4317    [CSR_PMPADDR15] =  { "pmpaddr15", pmp, read_pmpaddr, write_pmpaddr },
4318
4319    /* Debug CSRs */
4320    [CSR_TSELECT]   =  { "tselect", debug, read_tselect, write_tselect },
4321    [CSR_TDATA1]    =  { "tdata1",  debug, read_tdata,   write_tdata   },
4322    [CSR_TDATA2]    =  { "tdata2",  debug, read_tdata,   write_tdata   },
4323    [CSR_TDATA3]    =  { "tdata3",  debug, read_tdata,   write_tdata   },
4324    [CSR_TINFO]     =  { "tinfo",   debug, read_tinfo,   write_ignore  },
4325
4326    /* User Pointer Masking */
4327    [CSR_UMTE]    =    { "umte",    pointer_masking, read_umte,  write_umte },
4328    [CSR_UPMMASK] =    { "upmmask", pointer_masking, read_upmmask,
4329                         write_upmmask                                      },
4330    [CSR_UPMBASE] =    { "upmbase", pointer_masking, read_upmbase,
4331                         write_upmbase                                      },
4332    /* Machine Pointer Masking */
4333    [CSR_MMTE]    =    { "mmte",    pointer_masking, read_mmte,  write_mmte },
4334    [CSR_MPMMASK] =    { "mpmmask", pointer_masking, read_mpmmask,
4335                         write_mpmmask                                      },
4336    [CSR_MPMBASE] =    { "mpmbase", pointer_masking, read_mpmbase,
4337                         write_mpmbase                                      },
4338    /* Supervisor Pointer Masking */
4339    [CSR_SMTE]    =    { "smte",    pointer_masking, read_smte,  write_smte },
4340    [CSR_SPMMASK] =    { "spmmask", pointer_masking, read_spmmask,
4341                         write_spmmask                                      },
4342    [CSR_SPMBASE] =    { "spmbase", pointer_masking, read_spmbase,
4343                         write_spmbase                                      },
4344
4345    /* Performance Counters */
4346    [CSR_HPMCOUNTER3]    = { "hpmcounter3",    ctr,    read_hpmcounter },
4347    [CSR_HPMCOUNTER4]    = { "hpmcounter4",    ctr,    read_hpmcounter },
4348    [CSR_HPMCOUNTER5]    = { "hpmcounter5",    ctr,    read_hpmcounter },
4349    [CSR_HPMCOUNTER6]    = { "hpmcounter6",    ctr,    read_hpmcounter },
4350    [CSR_HPMCOUNTER7]    = { "hpmcounter7",    ctr,    read_hpmcounter },
4351    [CSR_HPMCOUNTER8]    = { "hpmcounter8",    ctr,    read_hpmcounter },
4352    [CSR_HPMCOUNTER9]    = { "hpmcounter9",    ctr,    read_hpmcounter },
4353    [CSR_HPMCOUNTER10]   = { "hpmcounter10",   ctr,    read_hpmcounter },
4354    [CSR_HPMCOUNTER11]   = { "hpmcounter11",   ctr,    read_hpmcounter },
4355    [CSR_HPMCOUNTER12]   = { "hpmcounter12",   ctr,    read_hpmcounter },
4356    [CSR_HPMCOUNTER13]   = { "hpmcounter13",   ctr,    read_hpmcounter },
4357    [CSR_HPMCOUNTER14]   = { "hpmcounter14",   ctr,    read_hpmcounter },
4358    [CSR_HPMCOUNTER15]   = { "hpmcounter15",   ctr,    read_hpmcounter },
4359    [CSR_HPMCOUNTER16]   = { "hpmcounter16",   ctr,    read_hpmcounter },
4360    [CSR_HPMCOUNTER17]   = { "hpmcounter17",   ctr,    read_hpmcounter },
4361    [CSR_HPMCOUNTER18]   = { "hpmcounter18",   ctr,    read_hpmcounter },
4362    [CSR_HPMCOUNTER19]   = { "hpmcounter19",   ctr,    read_hpmcounter },
4363    [CSR_HPMCOUNTER20]   = { "hpmcounter20",   ctr,    read_hpmcounter },
4364    [CSR_HPMCOUNTER21]   = { "hpmcounter21",   ctr,    read_hpmcounter },
4365    [CSR_HPMCOUNTER22]   = { "hpmcounter22",   ctr,    read_hpmcounter },
4366    [CSR_HPMCOUNTER23]   = { "hpmcounter23",   ctr,    read_hpmcounter },
4367    [CSR_HPMCOUNTER24]   = { "hpmcounter24",   ctr,    read_hpmcounter },
4368    [CSR_HPMCOUNTER25]   = { "hpmcounter25",   ctr,    read_hpmcounter },
4369    [CSR_HPMCOUNTER26]   = { "hpmcounter26",   ctr,    read_hpmcounter },
4370    [CSR_HPMCOUNTER27]   = { "hpmcounter27",   ctr,    read_hpmcounter },
4371    [CSR_HPMCOUNTER28]   = { "hpmcounter28",   ctr,    read_hpmcounter },
4372    [CSR_HPMCOUNTER29]   = { "hpmcounter29",   ctr,    read_hpmcounter },
4373    [CSR_HPMCOUNTER30]   = { "hpmcounter30",   ctr,    read_hpmcounter },
4374    [CSR_HPMCOUNTER31]   = { "hpmcounter31",   ctr,    read_hpmcounter },
4375
4376    [CSR_MHPMCOUNTER3]   = { "mhpmcounter3",   mctr,    read_hpmcounter,
4377                             write_mhpmcounter                         },
4378    [CSR_MHPMCOUNTER4]   = { "mhpmcounter4",   mctr,    read_hpmcounter,
4379                             write_mhpmcounter                         },
4380    [CSR_MHPMCOUNTER5]   = { "mhpmcounter5",   mctr,    read_hpmcounter,
4381                             write_mhpmcounter                         },
4382    [CSR_MHPMCOUNTER6]   = { "mhpmcounter6",   mctr,    read_hpmcounter,
4383                             write_mhpmcounter                         },
4384    [CSR_MHPMCOUNTER7]   = { "mhpmcounter7",   mctr,    read_hpmcounter,
4385                             write_mhpmcounter                         },
4386    [CSR_MHPMCOUNTER8]   = { "mhpmcounter8",   mctr,    read_hpmcounter,
4387                             write_mhpmcounter                         },
4388    [CSR_MHPMCOUNTER9]   = { "mhpmcounter9",   mctr,    read_hpmcounter,
4389                             write_mhpmcounter                         },
4390    [CSR_MHPMCOUNTER10]  = { "mhpmcounter10",  mctr,    read_hpmcounter,
4391                             write_mhpmcounter                         },
4392    [CSR_MHPMCOUNTER11]  = { "mhpmcounter11",  mctr,    read_hpmcounter,
4393                             write_mhpmcounter                         },
4394    [CSR_MHPMCOUNTER12]  = { "mhpmcounter12",  mctr,    read_hpmcounter,
4395                             write_mhpmcounter                         },
4396    [CSR_MHPMCOUNTER13]  = { "mhpmcounter13",  mctr,    read_hpmcounter,
4397                             write_mhpmcounter                         },
4398    [CSR_MHPMCOUNTER14]  = { "mhpmcounter14",  mctr,    read_hpmcounter,
4399                             write_mhpmcounter                         },
4400    [CSR_MHPMCOUNTER15]  = { "mhpmcounter15",  mctr,    read_hpmcounter,
4401                             write_mhpmcounter                         },
4402    [CSR_MHPMCOUNTER16]  = { "mhpmcounter16",  mctr,    read_hpmcounter,
4403                             write_mhpmcounter                         },
4404    [CSR_MHPMCOUNTER17]  = { "mhpmcounter17",  mctr,    read_hpmcounter,
4405                             write_mhpmcounter                         },
4406    [CSR_MHPMCOUNTER18]  = { "mhpmcounter18",  mctr,    read_hpmcounter,
4407                             write_mhpmcounter                         },
4408    [CSR_MHPMCOUNTER19]  = { "mhpmcounter19",  mctr,    read_hpmcounter,
4409                             write_mhpmcounter                         },
4410    [CSR_MHPMCOUNTER20]  = { "mhpmcounter20",  mctr,    read_hpmcounter,
4411                             write_mhpmcounter                         },
4412    [CSR_MHPMCOUNTER21]  = { "mhpmcounter21",  mctr,    read_hpmcounter,
4413                             write_mhpmcounter                         },
4414    [CSR_MHPMCOUNTER22]  = { "mhpmcounter22",  mctr,    read_hpmcounter,
4415                             write_mhpmcounter                         },
4416    [CSR_MHPMCOUNTER23]  = { "mhpmcounter23",  mctr,    read_hpmcounter,
4417                             write_mhpmcounter                         },
4418    [CSR_MHPMCOUNTER24]  = { "mhpmcounter24",  mctr,    read_hpmcounter,
4419                             write_mhpmcounter                         },
4420    [CSR_MHPMCOUNTER25]  = { "mhpmcounter25",  mctr,    read_hpmcounter,
4421                             write_mhpmcounter                         },
4422    [CSR_MHPMCOUNTER26]  = { "mhpmcounter26",  mctr,    read_hpmcounter,
4423                             write_mhpmcounter                         },
4424    [CSR_MHPMCOUNTER27]  = { "mhpmcounter27",  mctr,    read_hpmcounter,
4425                             write_mhpmcounter                         },
4426    [CSR_MHPMCOUNTER28]  = { "mhpmcounter28",  mctr,    read_hpmcounter,
4427                             write_mhpmcounter                         },
4428    [CSR_MHPMCOUNTER29]  = { "mhpmcounter29",  mctr,    read_hpmcounter,
4429                             write_mhpmcounter                         },
4430    [CSR_MHPMCOUNTER30]  = { "mhpmcounter30",  mctr,    read_hpmcounter,
4431                             write_mhpmcounter                         },
4432    [CSR_MHPMCOUNTER31]  = { "mhpmcounter31",  mctr,    read_hpmcounter,
4433                             write_mhpmcounter                         },
4434
4435    [CSR_MCOUNTINHIBIT]  = { "mcountinhibit",  any, read_mcountinhibit,
4436                             write_mcountinhibit,
4437                             .min_priv_ver = PRIV_VERSION_1_11_0       },
4438
4439    [CSR_MHPMEVENT3]     = { "mhpmevent3",     any,    read_mhpmevent,
4440                             write_mhpmevent                           },
4441    [CSR_MHPMEVENT4]     = { "mhpmevent4",     any,    read_mhpmevent,
4442                             write_mhpmevent                           },
4443    [CSR_MHPMEVENT5]     = { "mhpmevent5",     any,    read_mhpmevent,
4444                             write_mhpmevent                           },
4445    [CSR_MHPMEVENT6]     = { "mhpmevent6",     any,    read_mhpmevent,
4446                             write_mhpmevent                           },
4447    [CSR_MHPMEVENT7]     = { "mhpmevent7",     any,    read_mhpmevent,
4448                             write_mhpmevent                           },
4449    [CSR_MHPMEVENT8]     = { "mhpmevent8",     any,    read_mhpmevent,
4450                             write_mhpmevent                           },
4451    [CSR_MHPMEVENT9]     = { "mhpmevent9",     any,    read_mhpmevent,
4452                             write_mhpmevent                           },
4453    [CSR_MHPMEVENT10]    = { "mhpmevent10",    any,    read_mhpmevent,
4454                             write_mhpmevent                           },
4455    [CSR_MHPMEVENT11]    = { "mhpmevent11",    any,    read_mhpmevent,
4456                             write_mhpmevent                           },
4457    [CSR_MHPMEVENT12]    = { "mhpmevent12",    any,    read_mhpmevent,
4458                             write_mhpmevent                           },
4459    [CSR_MHPMEVENT13]    = { "mhpmevent13",    any,    read_mhpmevent,
4460                             write_mhpmevent                           },
4461    [CSR_MHPMEVENT14]    = { "mhpmevent14",    any,    read_mhpmevent,
4462                             write_mhpmevent                           },
4463    [CSR_MHPMEVENT15]    = { "mhpmevent15",    any,    read_mhpmevent,
4464                             write_mhpmevent                           },
4465    [CSR_MHPMEVENT16]    = { "mhpmevent16",    any,    read_mhpmevent,
4466                             write_mhpmevent                           },
4467    [CSR_MHPMEVENT17]    = { "mhpmevent17",    any,    read_mhpmevent,
4468                             write_mhpmevent                           },
4469    [CSR_MHPMEVENT18]    = { "mhpmevent18",    any,    read_mhpmevent,
4470                             write_mhpmevent                           },
4471    [CSR_MHPMEVENT19]    = { "mhpmevent19",    any,    read_mhpmevent,
4472                             write_mhpmevent                           },
4473    [CSR_MHPMEVENT20]    = { "mhpmevent20",    any,    read_mhpmevent,
4474                             write_mhpmevent                           },
4475    [CSR_MHPMEVENT21]    = { "mhpmevent21",    any,    read_mhpmevent,
4476                             write_mhpmevent                           },
4477    [CSR_MHPMEVENT22]    = { "mhpmevent22",    any,    read_mhpmevent,
4478                             write_mhpmevent                           },
4479    [CSR_MHPMEVENT23]    = { "mhpmevent23",    any,    read_mhpmevent,
4480                             write_mhpmevent                           },
4481    [CSR_MHPMEVENT24]    = { "mhpmevent24",    any,    read_mhpmevent,
4482                             write_mhpmevent                           },
4483    [CSR_MHPMEVENT25]    = { "mhpmevent25",    any,    read_mhpmevent,
4484                             write_mhpmevent                           },
4485    [CSR_MHPMEVENT26]    = { "mhpmevent26",    any,    read_mhpmevent,
4486                             write_mhpmevent                           },
4487    [CSR_MHPMEVENT27]    = { "mhpmevent27",    any,    read_mhpmevent,
4488                             write_mhpmevent                           },
4489    [CSR_MHPMEVENT28]    = { "mhpmevent28",    any,    read_mhpmevent,
4490                             write_mhpmevent                           },
4491    [CSR_MHPMEVENT29]    = { "mhpmevent29",    any,    read_mhpmevent,
4492                             write_mhpmevent                           },
4493    [CSR_MHPMEVENT30]    = { "mhpmevent30",    any,    read_mhpmevent,
4494                             write_mhpmevent                           },
4495    [CSR_MHPMEVENT31]    = { "mhpmevent31",    any,    read_mhpmevent,
4496                             write_mhpmevent                           },
4497
4498    [CSR_MHPMEVENT3H]    = { "mhpmevent3h",    sscofpmf,  read_mhpmeventh,
4499                             write_mhpmeventh,
4500                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4501    [CSR_MHPMEVENT4H]    = { "mhpmevent4h",    sscofpmf,  read_mhpmeventh,
4502                             write_mhpmeventh,
4503                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4504    [CSR_MHPMEVENT5H]    = { "mhpmevent5h",    sscofpmf,  read_mhpmeventh,
4505                             write_mhpmeventh,
4506                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4507    [CSR_MHPMEVENT6H]    = { "mhpmevent6h",    sscofpmf,  read_mhpmeventh,
4508                             write_mhpmeventh,
4509                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4510    [CSR_MHPMEVENT7H]    = { "mhpmevent7h",    sscofpmf,  read_mhpmeventh,
4511                             write_mhpmeventh,
4512                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4513    [CSR_MHPMEVENT8H]    = { "mhpmevent8h",    sscofpmf,  read_mhpmeventh,
4514                             write_mhpmeventh,
4515                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4516    [CSR_MHPMEVENT9H]    = { "mhpmevent9h",    sscofpmf,  read_mhpmeventh,
4517                             write_mhpmeventh,
4518                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4519    [CSR_MHPMEVENT10H]   = { "mhpmevent10h",    sscofpmf,  read_mhpmeventh,
4520                             write_mhpmeventh,
4521                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4522    [CSR_MHPMEVENT11H]   = { "mhpmevent11h",    sscofpmf,  read_mhpmeventh,
4523                             write_mhpmeventh,
4524                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4525    [CSR_MHPMEVENT12H]   = { "mhpmevent12h",    sscofpmf,  read_mhpmeventh,
4526                             write_mhpmeventh,
4527                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4528    [CSR_MHPMEVENT13H]   = { "mhpmevent13h",    sscofpmf,  read_mhpmeventh,
4529                             write_mhpmeventh,
4530                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4531    [CSR_MHPMEVENT14H]   = { "mhpmevent14h",    sscofpmf,  read_mhpmeventh,
4532                             write_mhpmeventh,
4533                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4534    [CSR_MHPMEVENT15H]   = { "mhpmevent15h",    sscofpmf,  read_mhpmeventh,
4535                             write_mhpmeventh,
4536                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4537    [CSR_MHPMEVENT16H]   = { "mhpmevent16h",    sscofpmf,  read_mhpmeventh,
4538                             write_mhpmeventh,
4539                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4540    [CSR_MHPMEVENT17H]   = { "mhpmevent17h",    sscofpmf,  read_mhpmeventh,
4541                             write_mhpmeventh,
4542                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4543    [CSR_MHPMEVENT18H]   = { "mhpmevent18h",    sscofpmf,  read_mhpmeventh,
4544                             write_mhpmeventh,
4545                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4546    [CSR_MHPMEVENT19H]   = { "mhpmevent19h",    sscofpmf,  read_mhpmeventh,
4547                             write_mhpmeventh,
4548                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4549    [CSR_MHPMEVENT20H]   = { "mhpmevent20h",    sscofpmf,  read_mhpmeventh,
4550                             write_mhpmeventh,
4551                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4552    [CSR_MHPMEVENT21H]   = { "mhpmevent21h",    sscofpmf,  read_mhpmeventh,
4553                             write_mhpmeventh,
4554                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4555    [CSR_MHPMEVENT22H]   = { "mhpmevent22h",    sscofpmf,  read_mhpmeventh,
4556                             write_mhpmeventh,
4557                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4558    [CSR_MHPMEVENT23H]   = { "mhpmevent23h",    sscofpmf,  read_mhpmeventh,
4559                             write_mhpmeventh,
4560                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4561    [CSR_MHPMEVENT24H]   = { "mhpmevent24h",    sscofpmf,  read_mhpmeventh,
4562                             write_mhpmeventh,
4563                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4564    [CSR_MHPMEVENT25H]   = { "mhpmevent25h",    sscofpmf,  read_mhpmeventh,
4565                             write_mhpmeventh,
4566                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4567    [CSR_MHPMEVENT26H]   = { "mhpmevent26h",    sscofpmf,  read_mhpmeventh,
4568                             write_mhpmeventh,
4569                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4570    [CSR_MHPMEVENT27H]   = { "mhpmevent27h",    sscofpmf,  read_mhpmeventh,
4571                             write_mhpmeventh,
4572                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4573    [CSR_MHPMEVENT28H]   = { "mhpmevent28h",    sscofpmf,  read_mhpmeventh,
4574                             write_mhpmeventh,
4575                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4576    [CSR_MHPMEVENT29H]   = { "mhpmevent29h",    sscofpmf,  read_mhpmeventh,
4577                             write_mhpmeventh,
4578                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4579    [CSR_MHPMEVENT30H]   = { "mhpmevent30h",    sscofpmf,  read_mhpmeventh,
4580                             write_mhpmeventh,
4581                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4582    [CSR_MHPMEVENT31H]   = { "mhpmevent31h",    sscofpmf,  read_mhpmeventh,
4583                             write_mhpmeventh,
4584                             .min_priv_ver = PRIV_VERSION_1_12_0        },
4585
4586    [CSR_HPMCOUNTER3H]   = { "hpmcounter3h",   ctr32,  read_hpmcounterh },
4587    [CSR_HPMCOUNTER4H]   = { "hpmcounter4h",   ctr32,  read_hpmcounterh },
4588    [CSR_HPMCOUNTER5H]   = { "hpmcounter5h",   ctr32,  read_hpmcounterh },
4589    [CSR_HPMCOUNTER6H]   = { "hpmcounter6h",   ctr32,  read_hpmcounterh },
4590    [CSR_HPMCOUNTER7H]   = { "hpmcounter7h",   ctr32,  read_hpmcounterh },
4591    [CSR_HPMCOUNTER8H]   = { "hpmcounter8h",   ctr32,  read_hpmcounterh },
4592    [CSR_HPMCOUNTER9H]   = { "hpmcounter9h",   ctr32,  read_hpmcounterh },
4593    [CSR_HPMCOUNTER10H]  = { "hpmcounter10h",  ctr32,  read_hpmcounterh },
4594    [CSR_HPMCOUNTER11H]  = { "hpmcounter11h",  ctr32,  read_hpmcounterh },
4595    [CSR_HPMCOUNTER12H]  = { "hpmcounter12h",  ctr32,  read_hpmcounterh },
4596    [CSR_HPMCOUNTER13H]  = { "hpmcounter13h",  ctr32,  read_hpmcounterh },
4597    [CSR_HPMCOUNTER14H]  = { "hpmcounter14h",  ctr32,  read_hpmcounterh },
4598    [CSR_HPMCOUNTER15H]  = { "hpmcounter15h",  ctr32,  read_hpmcounterh },
4599    [CSR_HPMCOUNTER16H]  = { "hpmcounter16h",  ctr32,  read_hpmcounterh },
4600    [CSR_HPMCOUNTER17H]  = { "hpmcounter17h",  ctr32,  read_hpmcounterh },
4601    [CSR_HPMCOUNTER18H]  = { "hpmcounter18h",  ctr32,  read_hpmcounterh },
4602    [CSR_HPMCOUNTER19H]  = { "hpmcounter19h",  ctr32,  read_hpmcounterh },
4603    [CSR_HPMCOUNTER20H]  = { "hpmcounter20h",  ctr32,  read_hpmcounterh },
4604    [CSR_HPMCOUNTER21H]  = { "hpmcounter21h",  ctr32,  read_hpmcounterh },
4605    [CSR_HPMCOUNTER22H]  = { "hpmcounter22h",  ctr32,  read_hpmcounterh },
4606    [CSR_HPMCOUNTER23H]  = { "hpmcounter23h",  ctr32,  read_hpmcounterh },
4607    [CSR_HPMCOUNTER24H]  = { "hpmcounter24h",  ctr32,  read_hpmcounterh },
4608    [CSR_HPMCOUNTER25H]  = { "hpmcounter25h",  ctr32,  read_hpmcounterh },
4609    [CSR_HPMCOUNTER26H]  = { "hpmcounter26h",  ctr32,  read_hpmcounterh },
4610    [CSR_HPMCOUNTER27H]  = { "hpmcounter27h",  ctr32,  read_hpmcounterh },
4611    [CSR_HPMCOUNTER28H]  = { "hpmcounter28h",  ctr32,  read_hpmcounterh },
4612    [CSR_HPMCOUNTER29H]  = { "hpmcounter29h",  ctr32,  read_hpmcounterh },
4613    [CSR_HPMCOUNTER30H]  = { "hpmcounter30h",  ctr32,  read_hpmcounterh },
4614    [CSR_HPMCOUNTER31H]  = { "hpmcounter31h",  ctr32,  read_hpmcounterh },
4615
4616    [CSR_MHPMCOUNTER3H]  = { "mhpmcounter3h",  mctr32,  read_hpmcounterh,
4617                             write_mhpmcounterh                         },
4618    [CSR_MHPMCOUNTER4H]  = { "mhpmcounter4h",  mctr32,  read_hpmcounterh,
4619                             write_mhpmcounterh                         },
4620    [CSR_MHPMCOUNTER5H]  = { "mhpmcounter5h",  mctr32,  read_hpmcounterh,
4621                             write_mhpmcounterh                         },
4622    [CSR_MHPMCOUNTER6H]  = { "mhpmcounter6h",  mctr32,  read_hpmcounterh,
4623                             write_mhpmcounterh                         },
4624    [CSR_MHPMCOUNTER7H]  = { "mhpmcounter7h",  mctr32,  read_hpmcounterh,
4625                             write_mhpmcounterh                         },
4626    [CSR_MHPMCOUNTER8H]  = { "mhpmcounter8h",  mctr32,  read_hpmcounterh,
4627                             write_mhpmcounterh                         },
4628    [CSR_MHPMCOUNTER9H]  = { "mhpmcounter9h",  mctr32,  read_hpmcounterh,
4629                             write_mhpmcounterh                         },
4630    [CSR_MHPMCOUNTER10H] = { "mhpmcounter10h", mctr32,  read_hpmcounterh,
4631                             write_mhpmcounterh                         },
4632    [CSR_MHPMCOUNTER11H] = { "mhpmcounter11h", mctr32,  read_hpmcounterh,
4633                             write_mhpmcounterh                         },
4634    [CSR_MHPMCOUNTER12H] = { "mhpmcounter12h", mctr32,  read_hpmcounterh,
4635                             write_mhpmcounterh                         },
4636    [CSR_MHPMCOUNTER13H] = { "mhpmcounter13h", mctr32,  read_hpmcounterh,
4637                             write_mhpmcounterh                         },
4638    [CSR_MHPMCOUNTER14H] = { "mhpmcounter14h", mctr32,  read_hpmcounterh,
4639                             write_mhpmcounterh                         },
4640    [CSR_MHPMCOUNTER15H] = { "mhpmcounter15h", mctr32,  read_hpmcounterh,
4641                             write_mhpmcounterh                         },
4642    [CSR_MHPMCOUNTER16H] = { "mhpmcounter16h", mctr32,  read_hpmcounterh,
4643                             write_mhpmcounterh                         },
4644    [CSR_MHPMCOUNTER17H] = { "mhpmcounter17h", mctr32,  read_hpmcounterh,
4645                             write_mhpmcounterh                         },
4646    [CSR_MHPMCOUNTER18H] = { "mhpmcounter18h", mctr32,  read_hpmcounterh,
4647                             write_mhpmcounterh                         },
4648    [CSR_MHPMCOUNTER19H] = { "mhpmcounter19h", mctr32,  read_hpmcounterh,
4649                             write_mhpmcounterh                         },
4650    [CSR_MHPMCOUNTER20H] = { "mhpmcounter20h", mctr32,  read_hpmcounterh,
4651                             write_mhpmcounterh                         },
4652    [CSR_MHPMCOUNTER21H] = { "mhpmcounter21h", mctr32,  read_hpmcounterh,
4653                             write_mhpmcounterh                         },
4654    [CSR_MHPMCOUNTER22H] = { "mhpmcounter22h", mctr32,  read_hpmcounterh,
4655                             write_mhpmcounterh                         },
4656    [CSR_MHPMCOUNTER23H] = { "mhpmcounter23h", mctr32,  read_hpmcounterh,
4657                             write_mhpmcounterh                         },
4658    [CSR_MHPMCOUNTER24H] = { "mhpmcounter24h", mctr32,  read_hpmcounterh,
4659                             write_mhpmcounterh                         },
4660    [CSR_MHPMCOUNTER25H] = { "mhpmcounter25h", mctr32,  read_hpmcounterh,
4661                             write_mhpmcounterh                         },
4662    [CSR_MHPMCOUNTER26H] = { "mhpmcounter26h", mctr32,  read_hpmcounterh,
4663                             write_mhpmcounterh                         },
4664    [CSR_MHPMCOUNTER27H] = { "mhpmcounter27h", mctr32,  read_hpmcounterh,
4665                             write_mhpmcounterh                         },
4666    [CSR_MHPMCOUNTER28H] = { "mhpmcounter28h", mctr32,  read_hpmcounterh,
4667                             write_mhpmcounterh                         },
4668    [CSR_MHPMCOUNTER29H] = { "mhpmcounter29h", mctr32,  read_hpmcounterh,
4669                             write_mhpmcounterh                         },
4670    [CSR_MHPMCOUNTER30H] = { "mhpmcounter30h", mctr32,  read_hpmcounterh,
4671                             write_mhpmcounterh                         },
4672    [CSR_MHPMCOUNTER31H] = { "mhpmcounter31h", mctr32,  read_hpmcounterh,
4673                             write_mhpmcounterh                         },
4674    [CSR_SCOUNTOVF]      = { "scountovf", sscofpmf,  read_scountovf,
4675                             .min_priv_ver = PRIV_VERSION_1_12_0 },
4676
4677#endif /* !CONFIG_USER_ONLY */
4678};
4679