xmsr.c revision 276403
1153838Sdfr/*- 2153838Sdfr * Copyright (c) 2011 NetApp, Inc. 3153838Sdfr * All rights reserved. 4153838Sdfr * 5153838Sdfr * Redistribution and use in source and binary forms, with or without 6153838Sdfr * modification, are permitted provided that the following conditions 7153838Sdfr * are met: 8153838Sdfr * 1. Redistributions of source code must retain the above copyright 9153838Sdfr * notice, this list of conditions and the following disclaimer. 10153838Sdfr * 2. Redistributions in binary form must reproduce the above copyright 11153838Sdfr * notice, this list of conditions and the following disclaimer in the 12153838Sdfr * documentation and/or other materials provided with the distribution. 13153838Sdfr * 14153838Sdfr * THIS SOFTWARE IS PROVIDED BY NETAPP, INC ``AS IS'' AND 15153838Sdfr * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16153838Sdfr * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17153838Sdfr * ARE DISCLAIMED. IN NO EVENT SHALL NETAPP, INC OR CONTRIBUTORS BE LIABLE 18153838Sdfr * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19153838Sdfr * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20153838Sdfr * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21153838Sdfr * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22153838Sdfr * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23153838Sdfr * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24153838Sdfr * SUCH DAMAGE. 25153838Sdfr * 26153838Sdfr * $FreeBSD: stable/10/usr.sbin/bhyve/xmsr.c 276403 2014-12-30 08:24:14Z neel $ 27153838Sdfr */ 28153838Sdfr 29153838Sdfr#include <sys/cdefs.h> 30203027Sgavin__FBSDID("$FreeBSD: stable/10/usr.sbin/bhyve/xmsr.c 276403 2014-12-30 08:24:14Z neel $"); 31206622Suqs 32153838Sdfr#include <sys/types.h> 33153838Sdfr 34153838Sdfr#include <machine/cpufunc.h> 35153838Sdfr#include <machine/vmm.h> 36153838Sdfr#include <machine/specialreg.h> 37153838Sdfr 38153838Sdfr#include <vmmapi.h> 39153838Sdfr 40153838Sdfr#include <stdio.h> 41153838Sdfr#include <stdlib.h> 42153838Sdfr#include <string.h> 43153838Sdfr 44153838Sdfr#include "xmsr.h" 45153838Sdfr 46153838Sdfrstatic int cpu_vendor_intel, cpu_vendor_amd; 47153838Sdfr 48153838Sdfrint 49153838Sdfremulate_wrmsr(struct vmctx *ctx, int vcpu, uint32_t num, uint64_t val) 50153838Sdfr{ 51153838Sdfr 52153838Sdfr if (cpu_vendor_intel) { 53153838Sdfr switch (num) { 54153838Sdfr case 0xd04: /* Sandy Bridge uncore PMCs */ 55153838Sdfr case 0xc24: 56153838Sdfr return (0); 57153838Sdfr case MSR_BIOS_UPDT_TRIG: 58153838Sdfr return (0); 59153838Sdfr case MSR_BIOS_SIGN: 60153838Sdfr return (0); 61153838Sdfr default: 62153838Sdfr break; 63153838Sdfr } 64153838Sdfr } else if (cpu_vendor_amd) { 65153838Sdfr switch (num) { 66153838Sdfr case MSR_HWCR: 67153838Sdfr /* 68153838Sdfr * Ignore writes to hardware configuration MSR. 69153838Sdfr */ 70153838Sdfr return (0); 71153838Sdfr 72153838Sdfr case MSR_NB_CFG1: 73153838Sdfr case MSR_IC_CFG: 74153838Sdfr return (0); /* Ignore writes */ 75153838Sdfr 76153838Sdfr case MSR_PERFEVSEL0: 77153838Sdfr case MSR_PERFEVSEL1: 78153838Sdfr case MSR_PERFEVSEL2: 79153838Sdfr case MSR_PERFEVSEL3: 80153838Sdfr /* Ignore writes to the PerfEvtSel MSRs */ 81153838Sdfr return (0); 82153838Sdfr 83153838Sdfr case MSR_K7_PERFCTR0: 84153838Sdfr case MSR_K7_PERFCTR1: 85153838Sdfr case MSR_K7_PERFCTR2: 86153838Sdfr case MSR_K7_PERFCTR3: 87153838Sdfr /* Ignore writes to the PerfCtr MSRs */ 88153838Sdfr return (0); 89153838Sdfr 90153838Sdfr case MSR_P_STATE_CONTROL: 91153838Sdfr /* Ignore write to change the P-state */ 92153838Sdfr return (0); 93153838Sdfr 94153838Sdfr default: 95153838Sdfr break; 96153838Sdfr } 97153838Sdfr } 98153838Sdfr return (-1); 99153838Sdfr} 100153838Sdfr 101153838Sdfrint 102153838Sdfremulate_rdmsr(struct vmctx *ctx, int vcpu, uint32_t num, uint64_t *val) 103236746Sjoel{ 104153838Sdfr int error = 0; 105153838Sdfr 106153838Sdfr if (cpu_vendor_intel) { 107153838Sdfr switch (num) { 108153838Sdfr case MSR_BIOS_SIGN: 109153838Sdfr case MSR_IA32_PLATFORM_ID: 110153838Sdfr case MSR_PKG_ENERGY_STATUS: 111153838Sdfr case MSR_PP0_ENERGY_STATUS: 112153838Sdfr case MSR_PP1_ENERGY_STATUS: 113153838Sdfr case MSR_DRAM_ENERGY_STATUS: 114153838Sdfr *val = 0; 115236746Sjoel break; 116153838Sdfr case MSR_RAPL_POWER_UNIT: 117153838Sdfr /* 118153838Sdfr * Use the default value documented in section 119153838Sdfr * "RAPL Interfaces" in Intel SDM vol3. 120153838Sdfr */ 121153838Sdfr *val = 0x000a1003; 122153838Sdfr break; 123153838Sdfr default: 124153838Sdfr error = -1; 125153838Sdfr break; 126153838Sdfr } 127153838Sdfr } else if (cpu_vendor_amd) { 128153838Sdfr switch (num) { 129236746Sjoel case MSR_BIOS_SIGN: 130153838Sdfr *val = 0; 131153838Sdfr break; 132153838Sdfr case MSR_HWCR: 133153838Sdfr /* 134153838Sdfr * Bios and Kernel Developer's Guides for AMD Families 135153838Sdfr * 12H, 14H, 15H and 16H. 136153838Sdfr */ 137153838Sdfr *val = 0x01000010; /* Reset value */ 138203027Sgavin *val |= 1 << 9; /* MONITOR/MWAIT disable */ 139153838Sdfr break; 140153838Sdfr 141153838Sdfr case MSR_NB_CFG1: 142154811Sdfr case MSR_IC_CFG: 143154811Sdfr /* 144154811Sdfr * The reset value is processor family dependent so 145154811Sdfr * just return 0. 146154811Sdfr */ 147154811Sdfr *val = 0; 148154811Sdfr break; 149154811Sdfr 150154811Sdfr case MSR_PERFEVSEL0: 151154811Sdfr case MSR_PERFEVSEL1: 152154811Sdfr case MSR_PERFEVSEL2: 153154811Sdfr case MSR_PERFEVSEL3: 154154811Sdfr /* 155154811Sdfr * PerfEvtSel MSRs are not properly virtualized so just 156154811Sdfr * return zero. 157154811Sdfr */ 158154811Sdfr *val = 0; 159154811Sdfr break; 160154811Sdfr 161154811Sdfr case MSR_K7_PERFCTR0: 162154811Sdfr case MSR_K7_PERFCTR1: 163154811Sdfr case MSR_K7_PERFCTR2: 164154811Sdfr case MSR_K7_PERFCTR3: 165154811Sdfr /* 166154811Sdfr * PerfCtr MSRs are not properly virtualized so just 167154811Sdfr * return zero. 168 */ 169 *val = 0; 170 break; 171 172 case MSR_SMM_ADDR: 173 case MSR_SMM_MASK: 174 /* 175 * Return the reset value defined in the AMD Bios and 176 * Kernel Developer's Guide. 177 */ 178 *val = 0; 179 break; 180 181 case MSR_P_STATE_LIMIT: 182 case MSR_P_STATE_CONTROL: 183 case MSR_P_STATE_STATUS: 184 case MSR_P_STATE_CONFIG(0): /* P0 configuration */ 185 *val = 0; 186 break; 187 188 default: 189 error = -1; 190 break; 191 } 192 } else { 193 error = -1; 194 } 195 return (error); 196} 197 198int 199init_msr(void) 200{ 201 int error; 202 u_int regs[4]; 203 char cpu_vendor[13]; 204 205 do_cpuid(0, regs); 206 ((u_int *)&cpu_vendor)[0] = regs[1]; 207 ((u_int *)&cpu_vendor)[1] = regs[3]; 208 ((u_int *)&cpu_vendor)[2] = regs[2]; 209 cpu_vendor[12] = '\0'; 210 211 error = 0; 212 if (strcmp(cpu_vendor, "AuthenticAMD") == 0) { 213 cpu_vendor_amd = 1; 214 } else if (strcmp(cpu_vendor, "GenuineIntel") == 0) { 215 cpu_vendor_intel = 1; 216 } else { 217 fprintf(stderr, "Unknown cpu vendor \"%s\"\n", cpu_vendor); 218 error = -1; 219 } 220 return (error); 221} 222