Skip to content

Commit cac570b

Browse files
committed
Update private package.
1 parent ffd9a3d commit cac570b

3 files changed

Lines changed: 64 additions & 1 deletion

File tree

private-gen.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ var reWrites = []rewrite{
3232
var excludeNames = map[string]bool{"string": true, "join": true, "trim": true,
3333
// cpuid_test.go
3434
"t": true, "println": true, "logf": true, "log": true, "fatalf": true, "fatal": true,
35+
"maxuint32": true, "lastindex": true,
3536
}
3637

3738
var excludePrefixes = []string{"test", "benchmark"}

private/cpuid.go

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -175,6 +175,7 @@ type cpuInfo struct {
175175
family int // CPU family number
176176
model int // CPU model number
177177
cacheline int // Cache line size in bytes. Will be 0 if undetectable.
178+
hz int64 // Clock speed, if known
178179
cache struct {
179180
l1i int // L1 Instruction Cache (per core or shared). Will be -1 if undetected
180181
l1d int // L1 Data Cache (per core or shared). Will be -1 if undetected
@@ -222,6 +223,7 @@ func detect() {
222223
cpu.logicalcores = logicalCores()
223224
cpu.physicalcores = physicalCores()
224225
cpu.vendorid = vendorID()
226+
cpu.hz = hertz(cpu.brandname)
225227
cpu.cacheSize()
226228
}
227229

@@ -598,6 +600,65 @@ func (c cpuInfo) logicalcpu() int {
598600
return int(ebx >> 24)
599601
}
600602

603+
// hertz tries to compute the clock speed of the CPU. If leaf 15 is
604+
// supported, use it, otherwise parse the brand string. Yes, really.
605+
func hertz(model string) int64 {
606+
mfi := maxFunctionID()
607+
if mfi >= 0x15 {
608+
eax, ebx, ecx, _ := cpuid(0x15)
609+
if eax != 0 && ebx != 0 && ecx != 0 {
610+
return int64((int64(ecx) * int64(ebx)) / int64(eax))
611+
}
612+
}
613+
// computeHz determines the official rated speed of a CPU from its brand
614+
// string. This insanity is *actually the official documented way to do
615+
// this according to Intel*, prior to leaf 0x15 existing. The official
616+
// documentation only shows this working for exactly `x.xx` or `xxxx`
617+
// cases, e.g., `2.50GHz` or `1300MHz`; this parser will accept other
618+
// sizes.
619+
hz := strings.LastIndex(model, "Hz")
620+
if hz < 3 {
621+
return -1
622+
}
623+
var multiplier int64
624+
switch model[hz-1] {
625+
case 'M':
626+
multiplier = 1000 * 1000
627+
case 'G':
628+
multiplier = 1000 * 1000 * 1000
629+
case 'T':
630+
multiplier = 1000 * 1000 * 1000 * 1000
631+
}
632+
if multiplier == 0 {
633+
return -1
634+
}
635+
freq := int64(0)
636+
divisor := int64(0)
637+
decimalShift := int64(1)
638+
var i int
639+
for i = hz - 2; i >= 0 && model[i] != ' '; i-- {
640+
if model[i] >= '0' && model[i] <= '9' {
641+
freq += int64(model[i]-'0') * decimalShift
642+
decimalShift *= 10
643+
} else if model[i] == '.' {
644+
if divisor != 0 {
645+
return -1
646+
}
647+
divisor = decimalShift
648+
} else {
649+
return -1
650+
}
651+
}
652+
// we didn't find a space
653+
if i < 0 {
654+
return -1
655+
}
656+
if divisor != 0 {
657+
return (freq * multiplier) / divisor
658+
}
659+
return freq * multiplier
660+
}
661+
601662
// VM Will return true if the cpu id indicates we are in
602663
// a virtual machine. This is only a hint, and will very likely
603664
// have many false negatives.
@@ -849,7 +910,7 @@ func (c *cpuInfo) cacheSize() {
849910
if maxExtendedFunction() < 0x8000001D {
850911
return
851912
}
852-
for i := uint32(0); i < math.maxuint32; i++ {
913+
for i := uint32(0); i < math.MaxUint32; i++ {
853914
eax, ebx, ecx, _ := cpuidex(0x8000001D, i)
854915

855916
level := (eax >> 5) & 7

private/cpuid_test.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ func TestCPUID(t *testing.T) {
2727
t.Log("L1 Data Cache:", cpu.cache.l1d, "bytes")
2828
t.Log("L2 Cache:", cpu.cache.l2, "bytes")
2929
t.Log("L3 Cache:", cpu.cache.l3, "bytes")
30+
t.Log("Hz:", cpu.hz, "Hz")
3031

3132
if cpu.sse2() {
3233
t.Log("We have SSE2")

0 commit comments

Comments
 (0)