blob: 502a8cce92e67d417a02d398aec90b69cfc81e39 [file] [log] [blame]
//go:build darwin && arm64 && cgo
package m1cpu
// #cgo LDFLAGS: -framework CoreFoundation -framework IOKit
// #include <AvailabilityMacros.h>
// #include <CoreFoundation/CoreFoundation.h>
// #include <IOKit/IOKitLib.h>
// #include <sys/sysctl.h>
//
// #if !defined(MAC_OS_VERSION_12_0) || MAC_OS_X_VERSION_MIN_REQUIRED < MAC_OS_VERSION_12_0
// #define kIOMainPortDefault kIOMasterPortDefault
// #endif
//
// #define HzToGHz(hz) ((hz) / 1000000000.0)
//
// UInt64 global_pCoreHz;
// UInt64 global_eCoreHz;
// int global_pCoreCount;
// int global_eCoreCount;
// int global_pCoreL1InstCacheSize;
// int global_eCoreL1InstCacheSize;
// int global_pCoreL1DataCacheSize;
// int global_eCoreL1DataCacheSize;
// int global_pCoreL2CacheSize;
// int global_eCoreL2CacheSize;
// char global_brand[32];
//
// UInt64 getFrequency(CFTypeRef typeRef) {
// CFDataRef cfData = typeRef;
//
// CFIndex size = CFDataGetLength(cfData);
// UInt8 buf[size];
// CFDataGetBytes(cfData, CFRangeMake(0, size), buf);
//
// UInt8 b1 = buf[size-5];
// UInt8 b2 = buf[size-6];
// UInt8 b3 = buf[size-7];
// UInt8 b4 = buf[size-8];
//
// UInt64 pCoreHz = 0x00000000FFFFFFFF & ((b1<<24) | (b2 << 16) | (b3 << 8) | (b4));
// return pCoreHz;
// }
//
// int sysctl_int(const char * name) {
// int value = -1;
// size_t size = 8;
// sysctlbyname(name, &value, &size, NULL, 0);
// return value;
// }
//
// void sysctl_string(const char * name, char * dest) {
// size_t size = 32;
// sysctlbyname(name, dest, &size, NULL, 0);
// }
//
// void initialize() {
// global_pCoreCount = sysctl_int("hw.perflevel0.physicalcpu");
// global_eCoreCount = sysctl_int("hw.perflevel1.physicalcpu");
// global_pCoreL1InstCacheSize = sysctl_int("hw.perflevel0.l1icachesize");
// global_eCoreL1InstCacheSize = sysctl_int("hw.perflevel1.l1icachesize");
// global_pCoreL1DataCacheSize = sysctl_int("hw.perflevel0.l1dcachesize");
// global_eCoreL1DataCacheSize = sysctl_int("hw.perflevel1.l1dcachesize");
// global_pCoreL2CacheSize = sysctl_int("hw.perflevel0.l2cachesize");
// global_eCoreL2CacheSize = sysctl_int("hw.perflevel1.l2cachesize");
// sysctl_string("machdep.cpu.brand_string", global_brand);
//
// CFMutableDictionaryRef matching = IOServiceMatching("AppleARMIODevice");
// io_iterator_t iter;
// IOServiceGetMatchingServices(kIOMainPortDefault, matching, &iter);
//
// const size_t bufsize = 512;
// io_object_t obj;
// while ((obj = IOIteratorNext(iter))) {
// char class[bufsize];
// IOObjectGetClass(obj, class);
// char name[bufsize];
// IORegistryEntryGetName(obj, name);
//
// if (strncmp(name, "pmgr", bufsize) == 0) {
// CFTypeRef pCoreRef = IORegistryEntryCreateCFProperty(obj, CFSTR("voltage-states5-sram"), kCFAllocatorDefault, 0);
// CFTypeRef eCoreRef = IORegistryEntryCreateCFProperty(obj, CFSTR("voltage-states1-sram"), kCFAllocatorDefault, 0);
//
// long long pCoreHz = getFrequency(pCoreRef);
// long long eCoreHz = getFrequency(eCoreRef);
//
// global_pCoreHz = pCoreHz;
// global_eCoreHz = eCoreHz;
// return;
// }
// }
// }
//
// UInt64 eCoreHz() {
// return global_eCoreHz;
// }
//
// UInt64 pCoreHz() {
// return global_pCoreHz;
// }
//
// Float64 eCoreGHz() {
// return HzToGHz(global_eCoreHz);
// }
//
// Float64 pCoreGHz() {
// return HzToGHz(global_pCoreHz);
// }
//
// int pCoreCount() {
// return global_pCoreCount;
// }
//
// int eCoreCount() {
// return global_eCoreCount;
// }
//
// int pCoreL1InstCacheSize() {
// return global_pCoreL1InstCacheSize;
// }
//
// int pCoreL1DataCacheSize() {
// return global_pCoreL1DataCacheSize;
// }
//
// int pCoreL2CacheSize() {
// return global_pCoreL2CacheSize;
// }
//
// int eCoreL1InstCacheSize() {
// return global_eCoreL1InstCacheSize;
// }
//
// int eCoreL1DataCacheSize() {
// return global_eCoreL1DataCacheSize;
// }
//
// int eCoreL2CacheSize() {
// return global_eCoreL2CacheSize;
// }
//
// char * modelName() {
// return global_brand;
// }
import "C"
func init() {
C.initialize()
}
// IsAppleSilicon returns true on this platform.
func IsAppleSilicon() bool {
return true
}
// PCoreHZ returns the max frequency in Hertz of the P-Core of an Apple Silicon CPU.
func PCoreHz() uint64 {
return uint64(C.pCoreHz())
}
// ECoreHZ returns the max frequency in Hertz of the E-Core of an Apple Silicon CPU.
func ECoreHz() uint64 {
return uint64(C.eCoreHz())
}
// PCoreGHz returns the max frequency in Gigahertz of the P-Core of an Apple Silicon CPU.
func PCoreGHz() float64 {
return float64(C.pCoreGHz())
}
// ECoreGHz returns the max frequency in Gigahertz of the E-Core of an Apple Silicon CPU.
func ECoreGHz() float64 {
return float64(C.eCoreGHz())
}
// PCoreCount returns the number of physical P (performance) cores.
func PCoreCount() int {
return int(C.pCoreCount())
}
// ECoreCount returns the number of physical E (efficiency) cores.
func ECoreCount() int {
return int(C.eCoreCount())
}
// PCoreCacheSize returns the sizes of the P (performance) core cache sizes
// in the order of
//
// - L1 instruction cache
// - L1 data cache
// - L2 cache
func PCoreCache() (int, int, int) {
return int(C.pCoreL1InstCacheSize()),
int(C.pCoreL1DataCacheSize()),
int(C.pCoreL2CacheSize())
}
// ECoreCacheSize returns the sizes of the E (efficiency) core cache sizes
// in the order of
//
// - L1 instruction cache
// - L1 data cache
// - L2 cache
func ECoreCache() (int, int, int) {
return int(C.eCoreL1InstCacheSize()),
int(C.eCoreL1DataCacheSize()),
int(C.eCoreL2CacheSize())
}
// ModelName returns the model name of the CPU.
func ModelName() string {
return C.GoString(C.modelName())
}