summaryrefslogtreecommitdiffstats
path: root/vendor/github.com/klauspost/cpuid/v2/os_darwin_arm64.go
blob: 84b1acd2153836b50a95d7e95e16b6557629331c (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
// Copyright (c) 2020 Klaus Post, released under MIT License. See LICENSE file.

package cpuid

import (
	"runtime"
	"strings"

	"golang.org/x/sys/unix"
)

func detectOS(c *CPUInfo) bool {
	if runtime.GOOS != "ios" {
		tryToFillCPUInfoFomSysctl(c)
	}
	// There are no hw.optional sysctl values for the below features on Mac OS 11.0
	// to detect their supported state dynamically. Assume the CPU features that
	// Apple Silicon M1 supports to be available as a minimal set of features
	// to all Go programs running on darwin/arm64.
	// TODO: Add more if we know them.
	c.featureSet.setIf(runtime.GOOS != "ios", AESARM, PMULL, SHA1, SHA2)

	return true
}

func sysctlGetBool(name string) bool {
	value, err := unix.SysctlUint32(name)
	if err != nil {
		return false
	}
	return value != 0
}

func sysctlGetString(name string) string {
	value, err := unix.Sysctl(name)
	if err != nil {
		return ""
	}
	return value
}

func sysctlGetInt(unknown int, names ...string) int {
	for _, name := range names {
		value, err := unix.SysctlUint32(name)
		if err != nil {
			continue
		}
		if value != 0 {
			return int(value)
		}
	}
	return unknown
}

func sysctlGetInt64(unknown int, names ...string) int {
	for _, name := range names {
		value64, err := unix.SysctlUint64(name)
		if err != nil {
			continue
		}
		if int(value64) != unknown {
			return int(value64)
		}
	}
	return unknown
}

func setFeature(c *CPUInfo, name string, feature FeatureID) {
	c.featureSet.setIf(sysctlGetBool(name), feature)
}
func tryToFillCPUInfoFomSysctl(c *CPUInfo) {
	c.BrandName = sysctlGetString("machdep.cpu.brand_string")

	if len(c.BrandName) != 0 {
		c.VendorString = strings.Fields(c.BrandName)[0]
	}

	c.PhysicalCores = sysctlGetInt(runtime.NumCPU(), "hw.physicalcpu")
	c.ThreadsPerCore = sysctlGetInt(1, "machdep.cpu.thread_count", "kern.num_threads") /
		sysctlGetInt(1, "hw.physicalcpu")
	c.LogicalCores = sysctlGetInt(runtime.NumCPU(), "machdep.cpu.core_count")
	c.Family = sysctlGetInt(0, "machdep.cpu.family", "hw.cpufamily")
	c.Model = sysctlGetInt(0, "machdep.cpu.model")
	c.CacheLine = sysctlGetInt64(0, "hw.cachelinesize")
	c.Cache.L1I = sysctlGetInt64(-1, "hw.l1icachesize")
	c.Cache.L1D = sysctlGetInt64(-1, "hw.l1dcachesize")
	c.Cache.L2 = sysctlGetInt64(-1, "hw.l2cachesize")
	c.Cache.L3 = sysctlGetInt64(-1, "hw.l3cachesize")

	// from https://developer.arm.com/downloads/-/exploration-tools/feature-names-for-a-profile
	setFeature(c, "hw.optional.arm.FEAT_AES", AESARM)
	setFeature(c, "hw.optional.AdvSIMD", ASIMD)
	setFeature(c, "hw.optional.arm.FEAT_DotProd", ASIMDDP)
	setFeature(c, "hw.optional.arm.FEAT_RDM", ASIMDRDM)
	setFeature(c, "hw.optional.FEAT_CRC32", CRC32)
	setFeature(c, "hw.optional.arm.FEAT_DPB", DCPOP)
	// setFeature(c, "", EVTSTRM)
	setFeature(c, "hw.optional.arm.FEAT_FCMA", FCMA)
	setFeature(c, "hw.optional.arm.FEAT_FP", FP)
	setFeature(c, "hw.optional.arm.FEAT_FP16", FPHP)
	setFeature(c, "hw.optional.arm.FEAT_PAuth", GPA)
	setFeature(c, "hw.optional.arm.FEAT_JSCVT", JSCVT)
	setFeature(c, "hw.optional.arm.FEAT_LRCPC", LRCPC)
	setFeature(c, "hw.optional.arm.FEAT_PMULL", PMULL)
	setFeature(c, "hw.optional.arm.FEAT_SHA1", SHA1)
	setFeature(c, "hw.optional.arm.FEAT_SHA256", SHA2)
	setFeature(c, "hw.optional.arm.FEAT_SHA3", SHA3)
	setFeature(c, "hw.optional.arm.FEAT_SHA512", SHA512)
	// setFeature(c, "", SM3)
	// setFeature(c, "", SM4)
	setFeature(c, "hw.optional.arm.FEAT_SVE", SVE)

	// from empirical observation
	setFeature(c, "hw.optional.AdvSIMD_HPFPCvt", ASIMDHP)
	setFeature(c, "hw.optional.armv8_1_atomics", ATOMICS)
	setFeature(c, "hw.optional.floatingpoint", FP)
	setFeature(c, "hw.optional.armv8_2_sha3", SHA3)
	setFeature(c, "hw.optional.armv8_2_sha512", SHA512)
	setFeature(c, "hw.optional.armv8_3_compnum", FCMA)
	setFeature(c, "hw.optional.armv8_crc32", CRC32)
}