github.com/ratrocket/u-root@v0.0.0-20180201221235-1cf9f48ee2cf/cmds/msr/msr.go (about) 1 // Copyright 2012-2017 the u-root Authors. All rights reserved 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // msr lets you read and write an msr for one or more cores. 6 // The cores are specified via a filepath.Glob string. 7 // The string should be for core number only, with no 8 // surrounding paths, e.g. you use 0 for core 0, not 9 // /dev/cpu/0/msr. 10 // To specify all cores, use '*' 11 // To specify all cores with two digits, use '??' 12 // To specify all odd cores, use '*[13579]' 13 // To specify, e.g., all the even cores, use '*[02468]'. 14 // Usage: 15 // msr r glob 32-bit-msr-number 16 // msr w glob 32-bit-msr-number 64-bit-value 17 // For each MSR operation msr will print an error if any. 18 // If your kernel does not have MSRs for any reason, 19 // this will fail due to file access. But it's quite possible 20 // that non-x86 architectures might someday implement MSRs, 21 // which on (e.g.) PPC might have a slightly different name 22 // (DICR) but would implement the same kinds of functions. 23 package main 24 25 import ( 26 "fmt" 27 "log" 28 "os" 29 "strconv" 30 ) 31 32 const usage = `msr r glob register 33 msr w glob register value` 34 35 func main() { 36 a := os.Args[1:] 37 if len(a) < 3 { 38 log.Fatal(usage) 39 } 40 41 m := msrList(a[1]) 42 43 reg, err := strconv.ParseUint(a[2], 0, 32) 44 if err != nil { 45 log.Fatalf("%v: %v", a[2], err) 46 } 47 switch a[0] { 48 case "r": 49 data, errs := rdmsr(m, uint32(reg)) 50 for i, v := range m { 51 if errs[i] != nil { 52 fmt.Printf("%v: %v\n", v, errs[i]) 53 } else { 54 fmt.Printf("%v: %#016x\n", v, data[i]) 55 } 56 } 57 58 case "w": 59 // Sadly, we don't get an error on write if the values 60 // don't match. Reading it back to check it is 61 // not always going to work. There are many write-only 62 // MSRs. If there are no errors there is still no 63 // guarantee that it worked, or if we read it we would 64 // see what we wrote, or that vmware did not do 65 // something stupid, or the x86 did not do something really 66 // stupid, or the particular implementation of the x86 67 // that we are on did not do something really stupid. 68 // Why is it this way? Because vendors hide proprietary 69 // information in hidden MSRs, or in hidden fields in MSRs. 70 // Checking is just not an option. There, feel better now? 71 if len(a) < 4 { 72 log.Fatal(usage) 73 } 74 v, err := strconv.ParseUint(a[3], 0, 64) 75 if err != nil { 76 log.Fatalf("%v: %v", a, err) 77 } 78 errs := wrmsr(m, uint32(reg), v) 79 for i, e := range errs { 80 if e != nil { 81 fmt.Printf("%v: %v\n", m[i], e) 82 } 83 } 84 85 default: 86 log.Fatalf(usage) 87 } 88 }