0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031 #ifndef __XEN_PUBLIC_ARCH_X86_MCA_H__
0032 #define __XEN_PUBLIC_ARCH_X86_MCA_H__
0033
0034
0035 #define __HYPERVISOR_mca __HYPERVISOR_arch_0
0036
0037 #define XEN_MCA_INTERFACE_VERSION 0x01ecc003
0038
0039
0040 #define XEN_MC_NONURGENT 0x1
0041
0042 #define XEN_MC_URGENT 0x2
0043
0044 #define XEN_MC_ACK 0x4
0045
0046
0047 #define XEN_MC_OK 0x0
0048
0049 #define XEN_MC_FETCHFAILED 0x1
0050
0051 #define XEN_MC_NODATA 0x2
0052
0053 #ifndef __ASSEMBLY__
0054
0055 #define VIRQ_MCA VIRQ_ARCH_0
0056
0057
0058
0059
0060
0061
0062
0063 #define MC_TYPE_GLOBAL 0
0064 #define MC_TYPE_BANK 1
0065 #define MC_TYPE_EXTENDED 2
0066 #define MC_TYPE_RECOVERY 3
0067
0068 struct mcinfo_common {
0069 uint16_t type;
0070 uint16_t size;
0071 };
0072
0073 #define MC_FLAG_CORRECTABLE (1 << 0)
0074 #define MC_FLAG_UNCORRECTABLE (1 << 1)
0075 #define MC_FLAG_RECOVERABLE (1 << 2)
0076 #define MC_FLAG_POLLED (1 << 3)
0077 #define MC_FLAG_RESET (1 << 4)
0078 #define MC_FLAG_CMCI (1 << 5)
0079 #define MC_FLAG_MCE (1 << 6)
0080
0081
0082 struct mcinfo_global {
0083 struct mcinfo_common common;
0084
0085 uint16_t mc_domid;
0086 uint16_t mc_vcpuid;
0087 uint32_t mc_socketid;
0088 uint16_t mc_coreid;
0089 uint16_t mc_core_threadid;
0090 uint32_t mc_apicid;
0091 uint32_t mc_flags;
0092 uint64_t mc_gstatus;
0093 };
0094
0095
0096 struct mcinfo_bank {
0097 struct mcinfo_common common;
0098
0099 uint16_t mc_bank;
0100 uint16_t mc_domid;
0101 uint64_t mc_status;
0102 uint64_t mc_addr;
0103 uint64_t mc_misc;
0104 uint64_t mc_ctrl2;
0105 uint64_t mc_tsc;
0106 };
0107
0108 struct mcinfo_msr {
0109 uint64_t reg;
0110 uint64_t value;
0111 };
0112
0113
0114 struct mcinfo_extended {
0115 struct mcinfo_common common;
0116 uint32_t mc_msrs;
0117
0118
0119
0120
0121
0122 struct mcinfo_msr mc_msr[sizeof(void *) * 4];
0123 };
0124
0125
0126
0127
0128 #define REC_ACTION_RECOVERED (0x1 << 0)
0129
0130 #define REC_ACTION_NONE (0x1 << 1)
0131
0132 #define REC_ACTION_NEED_RESET (0x1 << 2)
0133
0134
0135
0136
0137
0138
0139
0140 #define MC_ACTION_PAGE_OFFLINE (0x1 << 0)
0141
0142 #define MC_ACTION_CPU_OFFLINE (0x1 << 1)
0143
0144 #define MC_ACTION_CACHE_SHRINK (0x1 << 2)
0145
0146
0147
0148
0149
0150 struct page_offline_action {
0151
0152 uint64_t mfn;
0153 uint64_t status;
0154 };
0155
0156 struct cpu_offline_action {
0157
0158 uint32_t mc_socketid;
0159 uint16_t mc_coreid;
0160 uint16_t mc_core_threadid;
0161 };
0162
0163 #define MAX_UNION_SIZE 16
0164 struct mcinfo_recovery {
0165 struct mcinfo_common common;
0166 uint16_t mc_bank;
0167 uint8_t action_flags;
0168 uint8_t action_types;
0169 union {
0170 struct page_offline_action page_retire;
0171 struct cpu_offline_action cpu_offline;
0172 uint8_t pad[MAX_UNION_SIZE];
0173 } action_info;
0174 };
0175
0176
0177 #define MCINFO_MAXSIZE 768
0178 struct mc_info {
0179
0180 uint32_t mi_nentries;
0181 uint32_t flags;
0182 uint64_t mi_data[(MCINFO_MAXSIZE - 1) / 8];
0183 };
0184 DEFINE_GUEST_HANDLE_STRUCT(mc_info);
0185
0186 #define __MC_MSR_ARRAYSIZE 8
0187 #define __MC_NMSRS 1
0188 #define MC_NCAPS 7
0189 struct mcinfo_logical_cpu {
0190 uint32_t mc_cpunr;
0191 uint32_t mc_chipid;
0192 uint16_t mc_coreid;
0193 uint16_t mc_threadid;
0194 uint32_t mc_apicid;
0195 uint32_t mc_clusterid;
0196 uint32_t mc_ncores;
0197 uint32_t mc_ncores_active;
0198 uint32_t mc_nthreads;
0199 uint32_t mc_cpuid_level;
0200 uint32_t mc_family;
0201 uint32_t mc_vendor;
0202 uint32_t mc_model;
0203 uint32_t mc_step;
0204 char mc_vendorid[16];
0205 char mc_brandid[64];
0206 uint32_t mc_cpu_caps[MC_NCAPS];
0207 uint32_t mc_cache_size;
0208 uint32_t mc_cache_alignment;
0209 uint32_t mc_nmsrvals;
0210 struct mcinfo_msr mc_msrvalues[__MC_MSR_ARRAYSIZE];
0211 };
0212 DEFINE_GUEST_HANDLE_STRUCT(mcinfo_logical_cpu);
0213
0214
0215
0216
0217
0218 #define x86_mcinfo_nentries(_mi) \
0219 ((_mi)->mi_nentries)
0220
0221
0222
0223
0224 #define x86_mcinfo_first(_mi) \
0225 ((struct mcinfo_common *)(_mi)->mi_data)
0226
0227
0228
0229
0230 #define x86_mcinfo_next(_mic) \
0231 ((struct mcinfo_common *)((uint8_t *)(_mic) + (_mic)->size))
0232
0233
0234
0235
0236
0237 static inline void x86_mcinfo_lookup(struct mcinfo_common **ret,
0238 struct mc_info *mi, uint16_t type)
0239 {
0240 uint32_t i;
0241 struct mcinfo_common *mic;
0242 bool found = 0;
0243
0244 if (!ret || !mi)
0245 return;
0246
0247 mic = x86_mcinfo_first(mi);
0248 for (i = 0; i < x86_mcinfo_nentries(mi); i++) {
0249 if (mic->type == type) {
0250 found = 1;
0251 break;
0252 }
0253 mic = x86_mcinfo_next(mic);
0254 }
0255
0256 *ret = found ? mic : NULL;
0257 }
0258
0259
0260
0261
0262 #define XEN_MC_fetch 1
0263 struct xen_mc_fetch {
0264
0265
0266
0267
0268
0269 uint32_t flags;
0270 uint32_t _pad0;
0271
0272 uint64_t fetch_id;
0273
0274
0275 GUEST_HANDLE(mc_info) data;
0276 };
0277 DEFINE_GUEST_HANDLE_STRUCT(xen_mc_fetch);
0278
0279
0280
0281
0282
0283 #define XEN_MC_notifydomain 2
0284 struct xen_mc_notifydomain {
0285
0286 uint16_t mc_domid;
0287 uint16_t mc_vcpuid;
0288
0289
0290 uint32_t flags;
0291 };
0292 DEFINE_GUEST_HANDLE_STRUCT(xen_mc_notifydomain);
0293
0294 #define XEN_MC_physcpuinfo 3
0295 struct xen_mc_physcpuinfo {
0296
0297 uint32_t ncpus;
0298 uint32_t _pad0;
0299
0300 GUEST_HANDLE(mcinfo_logical_cpu) info;
0301 };
0302
0303 #define XEN_MC_msrinject 4
0304 #define MC_MSRINJ_MAXMSRS 8
0305 struct xen_mc_msrinject {
0306
0307 uint32_t mcinj_cpunr;
0308 uint32_t mcinj_flags;
0309 uint32_t mcinj_count;
0310 uint32_t _pad0;
0311 struct mcinfo_msr mcinj_msr[MC_MSRINJ_MAXMSRS];
0312 };
0313
0314
0315 #define MC_MSRINJ_F_INTERPOSE 0x1
0316
0317 #define XEN_MC_mceinject 5
0318 struct xen_mc_mceinject {
0319 unsigned int mceinj_cpunr;
0320 };
0321
0322 struct xen_mc {
0323 uint32_t cmd;
0324 uint32_t interface_version;
0325 union {
0326 struct xen_mc_fetch mc_fetch;
0327 struct xen_mc_notifydomain mc_notifydomain;
0328 struct xen_mc_physcpuinfo mc_physcpuinfo;
0329 struct xen_mc_msrinject mc_msrinject;
0330 struct xen_mc_mceinject mc_mceinject;
0331 } u;
0332 };
0333 DEFINE_GUEST_HANDLE_STRUCT(xen_mc);
0334
0335
0336
0337
0338
0339
0340 struct xen_mce {
0341 __u64 status;
0342 __u64 misc;
0343 __u64 addr;
0344 __u64 mcgstatus;
0345 __u64 ip;
0346 __u64 tsc;
0347 __u64 time;
0348 __u8 cpuvendor;
0349 __u8 inject_flags;
0350 __u16 pad;
0351 __u32 cpuid;
0352 __u8 cs;
0353 __u8 bank;
0354 __u8 cpu;
0355 __u8 finished;
0356 __u32 extcpu;
0357 __u32 socketid;
0358 __u32 apicid;
0359 __u64 mcgcap;
0360 __u64 synd;
0361 __u64 ipid;
0362 __u64 ppin;
0363 };
0364
0365
0366
0367
0368
0369
0370
0371
0372 #define XEN_MCE_LOG_LEN 32
0373
0374 struct xen_mce_log {
0375 char signature[12];
0376 unsigned len;
0377 unsigned next;
0378 unsigned flags;
0379 unsigned recordlen;
0380 struct xen_mce entry[XEN_MCE_LOG_LEN];
0381 };
0382
0383 #define XEN_MCE_OVERFLOW 0
0384
0385 #define XEN_MCE_LOG_SIGNATURE "MACHINECHECK"
0386
0387 #define MCE_GET_RECORD_LEN _IOR('M', 1, int)
0388 #define MCE_GET_LOG_LEN _IOR('M', 2, int)
0389 #define MCE_GETCLEAR_FLAGS _IOR('M', 3, int)
0390
0391 #endif
0392 #endif