1 /* SPDX-License-Identifier: GPL-2.0-or-later */ 2 /* 3 * QEMU LoongArch Machine State 4 * 5 * Copyright (c) 2021 Loongson Technology Corporation Limited 6 */ 7 8 #include "qemu/osdep.h" 9 #include "cpu.h" 10 #include "migration/cpu.h" 11 #include "vec.h" 12 13 static const VMStateDescription vmstate_fpu_reg = { 14 .name = "fpu_reg", 15 .version_id = 1, 16 .minimum_version_id = 1, 17 .fields = (const VMStateField[]) { 18 VMSTATE_UINT64(UD(0), VReg), 19 VMSTATE_END_OF_LIST() 20 } 21 }; 22 23 #define VMSTATE_FPU_REGS(_field, _state, _start) \ 24 VMSTATE_STRUCT_SUB_ARRAY(_field, _state, _start, 32, 0, \ 25 vmstate_fpu_reg, fpr_t) 26 27 static bool fpu_needed(void *opaque) 28 { 29 LoongArchCPU *cpu = opaque; 30 31 return FIELD_EX64(cpu->env.cpucfg[2], CPUCFG2, FP); 32 } 33 34 static const VMStateDescription vmstate_fpu = { 35 .name = "cpu/fpu", 36 .version_id = 1, 37 .minimum_version_id = 1, 38 .needed = fpu_needed, 39 .fields = (const VMStateField[]) { 40 VMSTATE_FPU_REGS(env.fpr, LoongArchCPU, 0), 41 VMSTATE_UINT32(env.fcsr0, LoongArchCPU), 42 VMSTATE_BOOL_ARRAY(env.cf, LoongArchCPU, 8), 43 VMSTATE_END_OF_LIST() 44 }, 45 }; 46 47 static const VMStateDescription vmstate_lsxh_reg = { 48 .name = "lsxh_reg", 49 .version_id = 1, 50 .minimum_version_id = 1, 51 .fields = (const VMStateField[]) { 52 VMSTATE_UINT64(UD(1), VReg), 53 VMSTATE_END_OF_LIST() 54 } 55 }; 56 57 #define VMSTATE_LSXH_REGS(_field, _state, _start) \ 58 VMSTATE_STRUCT_SUB_ARRAY(_field, _state, _start, 32, 0, \ 59 vmstate_lsxh_reg, fpr_t) 60 61 static bool lsx_needed(void *opaque) 62 { 63 LoongArchCPU *cpu = opaque; 64 65 return FIELD_EX64(cpu->env.cpucfg[2], CPUCFG2, LSX); 66 } 67 68 static const VMStateDescription vmstate_lsx = { 69 .name = "cpu/lsx", 70 .version_id = 1, 71 .minimum_version_id = 1, 72 .needed = lsx_needed, 73 .fields = (const VMStateField[]) { 74 VMSTATE_LSXH_REGS(env.fpr, LoongArchCPU, 0), 75 VMSTATE_END_OF_LIST() 76 }, 77 }; 78 79 static const VMStateDescription vmstate_lasxh_reg = { 80 .name = "lasxh_reg", 81 .version_id = 1, 82 .minimum_version_id = 1, 83 .fields = (const VMStateField[]) { 84 VMSTATE_UINT64(UD(2), VReg), 85 VMSTATE_UINT64(UD(3), VReg), 86 VMSTATE_END_OF_LIST() 87 } 88 }; 89 90 #define VMSTATE_LASXH_REGS(_field, _state, _start) \ 91 VMSTATE_STRUCT_SUB_ARRAY(_field, _state, _start, 32, 0, \ 92 vmstate_lasxh_reg, fpr_t) 93 94 static bool lasx_needed(void *opaque) 95 { 96 LoongArchCPU *cpu = opaque; 97 98 return FIELD_EX64(cpu->env.cpucfg[2], CPUCFG2, LASX); 99 } 100 101 static const VMStateDescription vmstate_lasx = { 102 .name = "cpu/lasx", 103 .version_id = 1, 104 .minimum_version_id = 1, 105 .needed = lasx_needed, 106 .fields = (const VMStateField[]) { 107 VMSTATE_LASXH_REGS(env.fpr, LoongArchCPU, 0), 108 VMSTATE_END_OF_LIST() 109 }, 110 }; 111 112 /* TLB state */ 113 const VMStateDescription vmstate_tlb = { 114 .name = "cpu/tlb", 115 .version_id = 0, 116 .minimum_version_id = 0, 117 .fields = (const VMStateField[]) { 118 VMSTATE_UINT64(tlb_misc, LoongArchTLB), 119 VMSTATE_UINT64(tlb_entry0, LoongArchTLB), 120 VMSTATE_UINT64(tlb_entry1, LoongArchTLB), 121 VMSTATE_END_OF_LIST() 122 } 123 }; 124 125 /* LoongArch CPU state */ 126 const VMStateDescription vmstate_loongarch_cpu = { 127 .name = "cpu", 128 .version_id = 1, 129 .minimum_version_id = 1, 130 .fields = (const VMStateField[]) { 131 VMSTATE_UINTTL_ARRAY(env.gpr, LoongArchCPU, 32), 132 VMSTATE_UINTTL(env.pc, LoongArchCPU), 133 134 /* Remaining CSRs */ 135 VMSTATE_UINT64(env.CSR_CRMD, LoongArchCPU), 136 VMSTATE_UINT64(env.CSR_PRMD, LoongArchCPU), 137 VMSTATE_UINT64(env.CSR_EUEN, LoongArchCPU), 138 VMSTATE_UINT64(env.CSR_MISC, LoongArchCPU), 139 VMSTATE_UINT64(env.CSR_ECFG, LoongArchCPU), 140 VMSTATE_UINT64(env.CSR_ESTAT, LoongArchCPU), 141 VMSTATE_UINT64(env.CSR_ERA, LoongArchCPU), 142 VMSTATE_UINT64(env.CSR_BADV, LoongArchCPU), 143 VMSTATE_UINT64(env.CSR_BADI, LoongArchCPU), 144 VMSTATE_UINT64(env.CSR_EENTRY, LoongArchCPU), 145 VMSTATE_UINT64(env.CSR_TLBIDX, LoongArchCPU), 146 VMSTATE_UINT64(env.CSR_TLBEHI, LoongArchCPU), 147 VMSTATE_UINT64(env.CSR_TLBELO0, LoongArchCPU), 148 VMSTATE_UINT64(env.CSR_TLBELO1, LoongArchCPU), 149 VMSTATE_UINT64(env.CSR_ASID, LoongArchCPU), 150 VMSTATE_UINT64(env.CSR_PGDL, LoongArchCPU), 151 VMSTATE_UINT64(env.CSR_PGDH, LoongArchCPU), 152 VMSTATE_UINT64(env.CSR_PGD, LoongArchCPU), 153 VMSTATE_UINT64(env.CSR_PWCL, LoongArchCPU), 154 VMSTATE_UINT64(env.CSR_PWCH, LoongArchCPU), 155 VMSTATE_UINT64(env.CSR_STLBPS, LoongArchCPU), 156 VMSTATE_UINT64(env.CSR_RVACFG, LoongArchCPU), 157 VMSTATE_UINT64(env.CSR_PRCFG1, LoongArchCPU), 158 VMSTATE_UINT64(env.CSR_PRCFG2, LoongArchCPU), 159 VMSTATE_UINT64(env.CSR_PRCFG3, LoongArchCPU), 160 VMSTATE_UINT64_ARRAY(env.CSR_SAVE, LoongArchCPU, 16), 161 VMSTATE_UINT64(env.CSR_TID, LoongArchCPU), 162 VMSTATE_UINT64(env.CSR_TCFG, LoongArchCPU), 163 VMSTATE_UINT64(env.CSR_TVAL, LoongArchCPU), 164 VMSTATE_UINT64(env.CSR_CNTC, LoongArchCPU), 165 VMSTATE_UINT64(env.CSR_TICLR, LoongArchCPU), 166 VMSTATE_UINT64(env.CSR_LLBCTL, LoongArchCPU), 167 VMSTATE_UINT64(env.CSR_IMPCTL1, LoongArchCPU), 168 VMSTATE_UINT64(env.CSR_IMPCTL2, LoongArchCPU), 169 VMSTATE_UINT64(env.CSR_TLBRENTRY, LoongArchCPU), 170 VMSTATE_UINT64(env.CSR_TLBRBADV, LoongArchCPU), 171 VMSTATE_UINT64(env.CSR_TLBRERA, LoongArchCPU), 172 VMSTATE_UINT64(env.CSR_TLBRSAVE, LoongArchCPU), 173 VMSTATE_UINT64(env.CSR_TLBRELO0, LoongArchCPU), 174 VMSTATE_UINT64(env.CSR_TLBRELO1, LoongArchCPU), 175 VMSTATE_UINT64(env.CSR_TLBREHI, LoongArchCPU), 176 VMSTATE_UINT64(env.CSR_TLBRPRMD, LoongArchCPU), 177 VMSTATE_UINT64(env.CSR_MERRCTL, LoongArchCPU), 178 VMSTATE_UINT64(env.CSR_MERRINFO1, LoongArchCPU), 179 VMSTATE_UINT64(env.CSR_MERRINFO2, LoongArchCPU), 180 VMSTATE_UINT64(env.CSR_MERRENTRY, LoongArchCPU), 181 VMSTATE_UINT64(env.CSR_MERRERA, LoongArchCPU), 182 VMSTATE_UINT64(env.CSR_MERRSAVE, LoongArchCPU), 183 VMSTATE_UINT64(env.CSR_CTAG, LoongArchCPU), 184 VMSTATE_UINT64_ARRAY(env.CSR_DMW, LoongArchCPU, 4), 185 186 /* Debug CSRs */ 187 VMSTATE_UINT64(env.CSR_DBG, LoongArchCPU), 188 VMSTATE_UINT64(env.CSR_DERA, LoongArchCPU), 189 VMSTATE_UINT64(env.CSR_DSAVE, LoongArchCPU), 190 /* TLB */ 191 VMSTATE_STRUCT_ARRAY(env.tlb, LoongArchCPU, LOONGARCH_TLB_MAX, 192 0, vmstate_tlb, LoongArchTLB), 193 194 VMSTATE_END_OF_LIST() 195 }, 196 .subsections = (const VMStateDescription * const []) { 197 &vmstate_fpu, 198 &vmstate_lsx, 199 &vmstate_lasx, 200 NULL 201 } 202 }; 203