Documentation ¶
Overview ¶
Package cpuid provides basic functionality for creating and adjusting CPU feature sets.
To use FeatureSets, one should start with an existing FeatureSet (either a known platform, or HostFeatureSet()) and then add, remove, and test for features as desired.
For example: on x86, test for hardware extended state saving, and if we don't have it, don't expose AVX, which cannot be saved with fxsave.
if !HostFeatureSet().HasFeature(X86FeatureXSAVE) { exposedFeatures.Remove(X86FeatureAVX) }
Index ¶
- Constants
- func HostID(axArg, cxArg uint32) (ax, bx, cx, dx uint32)
- type Cache
- type CacheType
- type ErrIncompatible
- type Feature
- type FeatureSet
- func (fs *FeatureSet) AMD() bool
- func (fs *FeatureSet) Add(feature Feature)
- func (fs *FeatureSet) CheckHostCompatible() error
- func (fs *FeatureSet) EmulateID(origAx, origCx uint32) (ax, bx, cx, dx uint32)
- func (fs *FeatureSet) ExtendedStateSize() (size, align uint)
- func (fs *FeatureSet) FlagsString(cpuinfoOnly bool) string
- func (fs *FeatureSet) HasFeature(feature Feature) bool
- func (fs *FeatureSet) Intel() bool
- func (fs *FeatureSet) Remove(feature Feature)
- func (fs *FeatureSet) StateFields() []string
- func (fs *FeatureSet) StateLoad(stateSourceObject state.Source)
- func (fs *FeatureSet) StateSave(stateSinkObject state.Sink)
- func (fs *FeatureSet) StateTypeName() string
- func (fs *FeatureSet) Subtract(other *FeatureSet) (diff map[Feature]bool)
- func (fs *FeatureSet) UseXsave() bool
- func (fs *FeatureSet) UseXsaveopt() bool
- func (fs *FeatureSet) ValidXCR0Mask() uint64
- func (fs FeatureSet) WriteCPUInfoTo(cpu uint, b *bytes.Buffer)
Constants ¶
const ( XSAVEFeatureX87 = 1 << 0 XSAVEFeatureSSE = 1 << 1 XSAVEFeatureAVX = 1 << 2 XSAVEFeatureBNDREGS = 1 << 3 XSAVEFeatureBNDCSR = 1 << 4 XSAVEFeatureAVX512op = 1 << 5 XSAVEFeatureAVX512zmm0 = 1 << 6 XSAVEFeatureAVX512zmm16 = 1 << 7 XSAVEFeaturePKRU = 1 << 9 )
These are the extended floating point state features. They are used to enumerate floating point features in XCR0, XSTATE_BV, etc.
Variables ¶
This section is empty.
Functions ¶
Types ¶
type Cache ¶
type Cache struct { // Level is the hierarchical level of this cache (L1, L2, etc). Level uint32 // Type is the type of cache. Type CacheType // FullyAssociative indicates that entries may be placed in any block. FullyAssociative bool // Partitions is the number of physical partitions in the cache. Partitions uint32 // Ways is the number of ways of associativity in the cache. Ways uint32 // Sets is the number of sets in the cache. Sets uint32 // InvalidateHierarchical indicates that WBINVD/INVD from threads // sharing this cache acts upon lower level caches for threads sharing // this cache. InvalidateHierarchical bool // Inclusive indicates that this cache is inclusive of lower cache // levels. Inclusive bool // DirectMapped indicates that this cache is directly mapped from // address, rather than using a hash function. DirectMapped bool }
Cache describes the parameters of a single cache on the system.
+stateify savable
func (*Cache) StateFields ¶
func (*Cache) StateTypeName ¶
type CacheType ¶
type CacheType uint8
CacheType describes the type of a cache, as returned in eax[4:0] for eax=4.
const ( // CacheData is a data cache. CacheData CacheType // CacheInstruction is an instruction cache. CacheInstruction // CacheUnified is a unified instruction and data cache. CacheUnified )
type ErrIncompatible ¶
type ErrIncompatible struct {
// contains filtered or unexported fields
}
ErrIncompatible is returned by FeatureSet.HostCompatible if fs is not a subset of the host feature set.
type Feature ¶
type Feature int
Feature is a unique identifier for a particular cpu feature. We just use an int as a feature number on x86 and arm64.
On x86, features are numbered according to "blocks". Each block is 32 bits, and feature bits from the same source (cpuid leaf/level) are in the same block.
On arm64, features are numbered according to the ELF HWCAP definition. arch/arm64/include/uapi/asm/hwcap.h
const ( X86FeatureSSE3 Feature = iota X86FeaturePCLMULDQ X86FeatureDTES64 X86FeatureMONITOR X86FeatureDSCPL X86FeatureVMX X86FeatureSMX X86FeatureEST X86FeatureTM2 X86FeatureSSSE3 // Not a typo, "supplemental" SSE3. X86FeatureCNXTID X86FeatureSDBG X86FeatureFMA X86FeatureCX16 X86FeatureXTPR X86FeaturePDCM X86FeaturePCID X86FeatureDCA X86FeatureSSE4_1 X86FeatureSSE4_2 X86FeatureX2APIC X86FeatureMOVBE X86FeaturePOPCNT X86FeatureTSCD X86FeatureAES X86FeatureXSAVE X86FeatureOSXSAVE X86FeatureAVX X86FeatureF16C X86FeatureRDRAND )
Block 0 constants are all of the "basic" feature bits returned by a cpuid in ecx with eax=1.
const ( X86FeatureFPU Feature = 32 + iota X86FeatureVME X86FeatureDE X86FeaturePSE X86FeatureTSC X86FeatureMSR X86FeaturePAE X86FeatureMCE X86FeatureCX8 X86FeatureAPIC X86FeatureSEP X86FeatureMTRR X86FeaturePGE X86FeatureMCA X86FeatureCMOV X86FeaturePAT X86FeaturePSE36 X86FeaturePSN X86FeatureCLFSH X86FeatureDS X86FeatureACPI X86FeatureMMX X86FeatureFXSR X86FeatureSSE X86FeatureSSE2 X86FeatureSS X86FeatureHTT X86FeatureTM X86FeatureIA64 X86FeaturePBE )
Block 1 constants are all of the "basic" feature bits returned by a cpuid in edx with eax=1.
const ( X86FeatureFSGSBase Feature = 2*32 + iota X86FeatureTSC_ADJUST X86FeatureBMI1 X86FeatureHLE X86FeatureAVX2 X86FeatureFDP_EXCPTN_ONLY X86FeatureSMEP X86FeatureBMI2 X86FeatureERMS X86FeatureINVPCID X86FeatureRTM X86FeatureCQM X86FeatureFPCSDS X86FeatureMPX X86FeatureRDT X86FeatureAVX512F X86FeatureAVX512DQ X86FeatureRDSEED X86FeatureADX X86FeatureSMAP X86FeatureAVX512IFMA X86FeaturePCOMMIT X86FeatureCLFLUSHOPT X86FeatureCLWB X86FeatureIPT // Intel processor trace. X86FeatureAVX512PF X86FeatureAVX512ER X86FeatureAVX512CD X86FeatureSHA X86FeatureAVX512BW X86FeatureAVX512VL )
Block 2 bits are the "structured extended" features returned in ebx for eax=7, ecx=0.
const ( X86FeaturePREFETCHWT1 Feature = 3*32 + iota X86FeatureAVX512VBMI X86FeatureUMIP X86FeaturePKU X86FeatureOSPKE X86FeatureWAITPKG X86FeatureAVX512_VBMI2 X86FeatureGFNI X86FeatureVAES X86FeatureVPCLMULQDQ X86FeatureAVX512_VNNI X86FeatureAVX512_BITALG X86FeatureTME X86FeatureAVX512_VPOPCNTDQ X86FeatureLA57 X86FeatureRDPID X86FeatureCLDEMOTE X86FeatureMOVDIRI X86FeatureMOVDIR64B )
Block 3 bits are the "extended" features returned in ecx for eax=7, ecx=0.
const ( X86FeatureXSAVEOPT Feature = 4*32 + iota X86FeatureXSAVEC X86FeatureXGETBV1 X86FeatureXSAVES )
Block 4 constants are for xsave capabilities in CPUID.(EAX=0DH,ECX=01H):EAX. The CPUID leaf is available only if 'X86FeatureXSAVE' is present.
const ( X86FeatureLAHF64 Feature = 5*32 + iota X86FeatureCMP_LEGACY X86FeatureSVM X86FeatureEXTAPIC X86FeatureCR8_LEGACY X86FeatureLZCNT X86FeatureSSE4A X86FeatureMISALIGNSSE X86FeaturePREFETCHW X86FeatureOSVW X86FeatureIBS X86FeatureXOP X86FeatureSKINIT X86FeatureWDT X86FeatureLWP X86FeatureFMA4 X86FeatureTCE X86FeatureTBM X86FeatureTOPOLOGY X86FeaturePERFCTR_CORE X86FeaturePERFCTR_NB X86FeatureBPEXT X86FeaturePERFCTR_TSC X86FeaturePERFCTR_LLC X86FeatureMWAITX // TODO(b/152776797): Some CPUs set this but it is not documented anywhere. X86FeatureBlock5Bit30 )
Block 5 constants are the extended feature bits in CPUID.(EAX=0x80000001):ECX.
const ( X86FeatureSYSCALL Feature = 6*32 + 11 X86FeatureNX Feature = 6*32 + 20 X86FeatureMMXEXT Feature = 6*32 + 22 X86FeatureFXSR_OPT Feature = 6*32 + 25 X86FeatureGBPAGES Feature = 6*32 + 26 X86FeatureRDTSCP Feature = 6*32 + 27 X86FeatureLM Feature = 6*32 + 29 X86Feature3DNOWEXT Feature = 6*32 + 30 X86Feature3DNOW Feature = 6*32 + 31 )
Block 6 constants are the extended feature bits in CPUID.(EAX=0x80000001):EDX.
These are sparse, and so the bit positions are assigned manually.
func FeatureFromString ¶
FeatureFromString returns the Feature associated with the given feature string plus a bool to indicate if it could find the feature.
type FeatureSet ¶
type FeatureSet struct { // Set is the set of features that are enabled in this FeatureSet. Set map[Feature]bool // VendorID is the 12-char string returned in ebx:edx:ecx for eax=0. VendorID string // ExtendedFamily is part of the processor signature. ExtendedFamily uint8 // ExtendedModel is part of the processor signature. ExtendedModel uint8 // ProcessorType is part of the processor signature. ProcessorType uint8 // Family is part of the processor signature. Family uint8 // Model is part of the processor signature. Model uint8 // SteppingID is part of the processor signature. SteppingID uint8 // Caches describes the caches on the CPU. Caches []Cache // CacheLine is the size of a cache line in bytes. // // All caches use the same line size. This is not enforced in the CPUID // encoding, but is true on all known x86 processors. CacheLine uint32 }
FeatureSet is a set of Features for a CPU.
+stateify savable
func HostFeatureSet ¶
func HostFeatureSet() *FeatureSet
HostFeatureSet uses cpuid to get host values and construct a feature set that matches that of the host machine. Note that there are several places where there appear to be some unnecessary assignments between register names (ax, bx, cx, or dx) and featureBlockN variables. This is to explicitly show where the different feature blocks come from, to make the code easier to inspect and read.
func (*FeatureSet) AMD ¶
func (fs *FeatureSet) AMD() bool
AMD returns true if fs describes an AMD CPU.
func (*FeatureSet) Add ¶
func (fs *FeatureSet) Add(feature Feature)
Add adds a Feature to a FeatureSet. It ignores duplicate features.
func (*FeatureSet) CheckHostCompatible ¶
func (fs *FeatureSet) CheckHostCompatible() error
CheckHostCompatible returns nil if fs is a subset of the host feature set.
func (*FeatureSet) EmulateID ¶
func (fs *FeatureSet) EmulateID(origAx, origCx uint32) (ax, bx, cx, dx uint32)
EmulateID emulates a cpuid instruction based on the feature set.
func (*FeatureSet) ExtendedStateSize ¶
func (fs *FeatureSet) ExtendedStateSize() (size, align uint)
ExtendedStateSize returns the number of bytes needed to save the "extended state" for this processor and the boundary it must be aligned to. Extended state includes floating point registers, and other cpu state that's not associated with the normal task context.
Note: We can save some space here with an optimization where we use a smaller chunk of memory depending on features that are actually enabled. Currently we just use the largest possible size for simplicity (which is about 2.5K worst case, with avx512).
func (*FeatureSet) FlagsString ¶
func (fs *FeatureSet) FlagsString(cpuinfoOnly bool) string
FlagsString prints out supported CPU flags. If cpuinfoOnly is true, it is equivalent to the "flags" field in /proc/cpuinfo.
func (*FeatureSet) HasFeature ¶
func (fs *FeatureSet) HasFeature(feature Feature) bool
HasFeature tests whether or not a feature is in the given feature set.
func (*FeatureSet) Intel ¶
func (fs *FeatureSet) Intel() bool
Intel returns true if fs describes an Intel CPU.
func (*FeatureSet) Remove ¶
func (fs *FeatureSet) Remove(feature Feature)
Remove removes a Feature from a FeatureSet. It ignores features that are not in the FeatureSet.
func (*FeatureSet) StateFields ¶
func (fs *FeatureSet) StateFields() []string
func (*FeatureSet) StateLoad ¶
func (fs *FeatureSet) StateLoad(stateSourceObject state.Source)
+checklocksignore
func (*FeatureSet) StateSave ¶
func (fs *FeatureSet) StateSave(stateSinkObject state.Sink)
+checklocksignore
func (*FeatureSet) StateTypeName ¶
func (fs *FeatureSet) StateTypeName() string
func (*FeatureSet) Subtract ¶
func (fs *FeatureSet) Subtract(other *FeatureSet) (diff map[Feature]bool)
Subtract returns the features present in fs that are not present in other. If all features in fs are present in other, Subtract returns nil.
func (*FeatureSet) UseXsave ¶
func (fs *FeatureSet) UseXsave() bool
UseXsave returns the choice of fp state saving instruction.
func (*FeatureSet) UseXsaveopt ¶
func (fs *FeatureSet) UseXsaveopt() bool
UseXsaveopt returns true if 'fs' supports the "xsaveopt" instruction.
func (*FeatureSet) ValidXCR0Mask ¶
func (fs *FeatureSet) ValidXCR0Mask() uint64
ValidXCR0Mask returns the bits that may be set to 1 in control register XCR0.
func (FeatureSet) WriteCPUInfoTo ¶
func (fs FeatureSet) WriteCPUInfoTo(cpu uint, b *bytes.Buffer)
WriteCPUInfoTo is to generate a section of one cpu in /proc/cpuinfo. This is a minimal /proc/cpuinfo, it is missing some fields like "microcode" that are not always printed in Linux. The bogomips field is simply made up.