Compare commits

...

4 Commits
v1.02 ... m1

Author SHA1 Message Date
Dr-Noob
ecce0354e5 [v1.02][ARM] Fixed M2 bug, support for M2 should now be complete 2022-09-05 18:17:15 +02:00
Dr-Noob
dfec2a65d2 [v1.02][ARM] Experimental support for M2 2022-09-05 10:02:26 +02:00
Dr-Noob
758be60967 [v1.02] Remove wrong check in udev 2022-09-05 08:24:22 +02:00
Dr-Noob
52ba038527 [v1.02][ARM] Add support for M1 Ultra 2022-05-25 22:11:48 +01:00
6 changed files with 123 additions and 22 deletions

View File

@@ -273,11 +273,46 @@ void fill_cpu_info_firestorm_icestorm(struct cpuInfo* cpu, uint32_t pcores, uint
fire->next_cpu = NULL; fire->next_cpu = NULL;
} }
void fill_cpu_info_avalanche_blizzard(struct cpuInfo* cpu, uint32_t pcores, uint32_t ecores) {
// 1. Fill BLIZZARD
struct cpuInfo* bli = cpu;
bli->midr = MIDR_APPLE_M2_BLIZZARD;
bli->arch = get_uarch_from_midr(bli->midr, bli);
bli->cach = get_cache_info(bli);
bli->feat = get_features_info();
bli->topo = malloc(sizeof(struct topology));
bli->topo->cach = bli->cach;
bli->topo->total_cores = pcores;
bli->freq = malloc(sizeof(struct frequency));
bli->freq->base = UNKNOWN_DATA;
bli->freq->max = 2800;
bli->hv = malloc(sizeof(struct hypervisor));
bli->hv->present = false;
bli->next_cpu = malloc(sizeof(struct cpuInfo));
// 2. Fill AVALANCHE
struct cpuInfo* ava = bli->next_cpu;
ava->midr = MIDR_APPLE_M2_AVALANCHE;
ava->arch = get_uarch_from_midr(ava->midr, ava);
ava->cach = get_cache_info(ava);
ava->feat = get_features_info();
ava->topo = malloc(sizeof(struct topology));
ava->topo->cach = ava->cach;
ava->topo->total_cores = ecores;
ava->freq = malloc(sizeof(struct frequency));
ava->freq->base = UNKNOWN_DATA;
ava->freq->max = 3500;
ava->hv = malloc(sizeof(struct hypervisor));
ava->hv->present = false;
ava->next_cpu = NULL;
}
struct cpuInfo* get_cpu_info_mach(struct cpuInfo* cpu) { struct cpuInfo* get_cpu_info_mach(struct cpuInfo* cpu) {
uint32_t cpu_family = get_sys_info_by_name("hw.cpufamily"); uint32_t cpu_family = get_sys_info_by_name("hw.cpufamily");
// Manually fill the cpuInfo assuming that the CPU // Manually fill the cpuInfo assuming that
// is a ARM_FIRESTORM_ICESTORM (Apple M1) // the CPU is an Apple M1/M2
if(cpu_family == CPUFAMILY_ARM_FIRESTORM_ICESTORM) { if(cpu_family == CPUFAMILY_ARM_FIRESTORM_ICESTORM) {
cpu->num_cpus = 2; cpu->num_cpus = 2;
// Now detect the M1 version // Now detect the M1 version
@@ -287,13 +322,20 @@ struct cpuInfo* get_cpu_info_mach(struct cpuInfo* cpu) {
fill_cpu_info_firestorm_icestorm(cpu, 4, 4); fill_cpu_info_firestorm_icestorm(cpu, 4, 4);
} }
else if(cpu_subfamily == CPUSUBFAMILY_ARM_HS || cpu_subfamily == CPUSUBFAMILY_ARM_HC_HD) { else if(cpu_subfamily == CPUSUBFAMILY_ARM_HS || cpu_subfamily == CPUSUBFAMILY_ARM_HC_HD) {
// Apple M1 Pro/Max. Detect number of cores // Apple M1 Pro/Max/Ultra. Detect number of cores
uint32_t physicalcpu = get_sys_info_by_name("hw.physicalcpu"); uint32_t physicalcpu = get_sys_info_by_name("hw.physicalcpu");
if(physicalcpu < 8 || physicalcpu > 10) { if(physicalcpu == 20) {
printBug("Found invalid physicalcpu: 0x%.8X", physicalcpu); // M1 Ultra
fill_cpu_info_firestorm_icestorm(cpu, 16, 4);
}
else if(physicalcpu == 8 || physicalcpu == 10) {
// M1 Pro/Max
fill_cpu_info_firestorm_icestorm(cpu, physicalcpu-2, 2);
}
else {
printBug("Found invalid physical cpu number: %d", physicalcpu);
return NULL; return NULL;
} }
fill_cpu_info_firestorm_icestorm(cpu, physicalcpu-2, 2);
} }
else { else {
printBug("Found invalid cpu_subfamily: 0x%.8X", cpu_subfamily); printBug("Found invalid cpu_subfamily: 0x%.8X", cpu_subfamily);
@@ -302,6 +344,13 @@ struct cpuInfo* get_cpu_info_mach(struct cpuInfo* cpu) {
cpu->soc = get_soc(); cpu->soc = get_soc();
cpu->peak_performance = get_peak_performance(cpu); cpu->peak_performance = get_peak_performance(cpu);
} }
else if(cpu_family == CPUFAMILY_ARM_AVALANCHE_BLIZZARD) {
// Just the "normal" M2 exists for now
cpu->num_cpus = 2;
fill_cpu_info_avalanche_blizzard(cpu, 4, 4);
cpu->soc = get_soc();
cpu->peak_performance = get_peak_performance(cpu);
}
else { else {
printBug("Found invalid cpu_family: 0x%.8X", cpu_family); printBug("Found invalid cpu_family: 0x%.8X", cpu_family);
return NULL; return NULL;

View File

@@ -648,7 +648,11 @@ struct system_on_chip* guess_soc_raspbery_pi(struct system_on_chip* soc) {
#if defined(__APPLE__) || defined(__MACH__) #if defined(__APPLE__) || defined(__MACH__)
struct system_on_chip* guess_soc_apple(struct system_on_chip* soc) { struct system_on_chip* guess_soc_apple(struct system_on_chip* soc) {
uint32_t cpu_family = get_sys_info_by_name("hw.cpufamily");
uint32_t cpu_subfamily = get_sys_info_by_name("hw.cpusubfamily"); uint32_t cpu_subfamily = get_sys_info_by_name("hw.cpusubfamily");
if(cpu_family == CPUFAMILY_ARM_FIRESTORM_ICESTORM) {
// Check M1 version
if(cpu_subfamily == CPUSUBFAMILY_ARM_HG) { if(cpu_subfamily == CPUSUBFAMILY_ARM_HG) {
fill_soc(soc, "M1", SOC_APPLE_M1, 5); fill_soc(soc, "M1", SOC_APPLE_M1, 5);
} }
@@ -656,8 +660,38 @@ struct system_on_chip* guess_soc_apple(struct system_on_chip* soc) {
fill_soc(soc, "M1 Pro", SOC_APPLE_M1_PRO, 5); fill_soc(soc, "M1 Pro", SOC_APPLE_M1_PRO, 5);
} }
else if(cpu_subfamily == CPUSUBFAMILY_ARM_HC_HD) { else if(cpu_subfamily == CPUSUBFAMILY_ARM_HC_HD) {
// Could be M1 Max or M1 Ultra (2x M1 Max)
uint32_t physicalcpu = get_sys_info_by_name("hw.physicalcpu");
if(physicalcpu == 20) {
fill_soc(soc, "M1 Ultra", SOC_APPLE_M1_ULTRA, 5);
}
else if(physicalcpu == 10) {
fill_soc(soc, "M1 Max", SOC_APPLE_M1_MAX, 5); fill_soc(soc, "M1 Max", SOC_APPLE_M1_MAX, 5);
} }
else {
printBug("Found invalid physical cpu number: %d", physicalcpu);
soc->soc_vendor = SOC_VENDOR_UNKNOWN;
}
}
else {
printBug("Found invalid cpu_subfamily: 0x%.8X", cpu_subfamily);
soc->soc_vendor = SOC_VENDOR_UNKNOWN;
}
}
else if(cpu_family == CPUFAMILY_ARM_AVALANCHE_BLIZZARD) {
// Check M2 version
if(cpu_subfamily == CPUSUBFAMILY_ARM_HG) {
fill_soc(soc, "M2", SOC_APPLE_M2, 5);
}
else {
printBug("Found invalid cpu_subfamily: 0x%.8X", cpu_subfamily);
soc->soc_vendor = SOC_VENDOR_UNKNOWN;
}
}
else {
printBug("Found invalid cpu_family: 0x%.8X", cpu_family);
soc->soc_vendor = SOC_VENDOR_UNKNOWN;
}
return soc; return soc;
} }
#endif #endif

View File

@@ -256,6 +256,8 @@ enum {
SOC_APPLE_M1, SOC_APPLE_M1,
SOC_APPLE_M1_PRO, SOC_APPLE_M1_PRO,
SOC_APPLE_M1_MAX, SOC_APPLE_M1_MAX,
SOC_APPLE_M1_ULTRA,
SOC_APPLE_M2,
// ALLWINNER // ALLWINNER
SOC_ALLWINNER_A10, SOC_ALLWINNER_A10,
SOC_ALLWINNER_A13, SOC_ALLWINNER_A13,
@@ -288,7 +290,7 @@ inline static VENDOR get_soc_vendor_from_soc(SOC soc) {
else if(soc >= SOC_EXYNOS_3475 && soc <= SOC_EXYNOS_880) return SOC_VENDOR_EXYNOS; else if(soc >= SOC_EXYNOS_3475 && soc <= SOC_EXYNOS_880) return SOC_VENDOR_EXYNOS;
else if(soc >= SOC_MTK_MT6893 && soc <= SOC_MTK_MT8783) return SOC_VENDOR_MEDIATEK; else if(soc >= SOC_MTK_MT6893 && soc <= SOC_MTK_MT8783) return SOC_VENDOR_MEDIATEK;
else if(soc >= SOC_SNAPD_QSD8650 && soc <= SOC_SNAPD_SM8350) return SOC_VENDOR_SNAPDRAGON; else if(soc >= SOC_SNAPD_QSD8650 && soc <= SOC_SNAPD_SM8350) return SOC_VENDOR_SNAPDRAGON;
else if(soc >= SOC_APPLE_M1 && soc <= SOC_APPLE_M1_MAX) return SOC_VENDOR_APPLE; else if(soc >= SOC_APPLE_M1 && soc <= SOC_APPLE_M2) return SOC_VENDOR_APPLE;
else if(soc >= SOC_ALLWINNER_A10 && soc <= SOC_ALLWINNER_R328) return SOC_VENDOR_ALLWINNER; else if(soc >= SOC_ALLWINNER_A10 && soc <= SOC_ALLWINNER_R328) return SOC_VENDOR_ALLWINNER;
return SOC_VENDOR_UNKNOWN; return SOC_VENDOR_UNKNOWN;
} }

View File

@@ -4,9 +4,23 @@
// From Linux kernel: arch/arm64/include/asm/cputype.h // From Linux kernel: arch/arm64/include/asm/cputype.h
#define MIDR_APPLE_M1_ICESTORM 0x610F0220 #define MIDR_APPLE_M1_ICESTORM 0x610F0220
#define MIDR_APPLE_M1_FIRESTORM 0x610F0230 #define MIDR_APPLE_M1_FIRESTORM 0x610F0230
// Kernel does not include those, so I just assume that
// APPLE_CPU_PART_M2_BLIZZARD=0x30,M2_AVALANCHE=0x31
#define MIDR_APPLE_M2_BLIZZARD 0x610F0300
#define MIDR_APPLE_M2_AVALANCHE 0x610F0310
// M1 / A14
#ifndef CPUFAMILY_ARM_FIRESTORM_ICESTORM #ifndef CPUFAMILY_ARM_FIRESTORM_ICESTORM
#define CPUFAMILY_ARM_FIRESTORM_ICESTORM 0x1B588BB3 #define CPUFAMILY_ARM_FIRESTORM_ICESTORM 0x1B588BB3
#endif #endif
// M2 / A15
#ifndef CPUFAMILY_ARM_AVALANCHE_BLIZZARD
#define CPUFAMILY_ARM_AVALANCHE_BLIZZARD 0xDA33D83D
#endif
// For detecting different M1 types
// NOTE: Could also be achieved detecting different
// MIDR values (e.g., APPLE_CPU_PART_M1_ICESTORM_PRO)
#ifndef CPUSUBFAMILY_ARM_HG #ifndef CPUSUBFAMILY_ARM_HG
#define CPUSUBFAMILY_ARM_HG 2 #define CPUSUBFAMILY_ARM_HG 2
#endif #endif

View File

@@ -33,6 +33,7 @@ enum {
ISA_ARMv8_2_A, ISA_ARMv8_2_A,
ISA_ARMv8_3_A, ISA_ARMv8_3_A,
ISA_ARMv8_4_A, ISA_ARMv8_4_A,
ISA_ARMv8_5_A
}; };
enum { enum {
@@ -95,6 +96,8 @@ enum {
UARCH_THUNDER, // Apple A13 processor (little cores). UARCH_THUNDER, // Apple A13 processor (little cores).
UARCH_ICESTORM, // Apple M1 processor (little cores). UARCH_ICESTORM, // Apple M1 processor (little cores).
UARCH_FIRESTORM, // Apple M1 processor (big cores). UARCH_FIRESTORM, // Apple M1 processor (big cores).
UARCH_BLIZZARD, // Apple M2 processor (little cores).
UARCH_AVALANCHE, // Apple M2 processor (big cores).
// CAVIUM // CAVIUM
UARCH_THUNDERX, // Cavium ThunderX UARCH_THUNDERX, // Cavium ThunderX
UARCH_THUNDERX2, // Cavium ThunderX2 (originally Broadcom Vulkan). UARCH_THUNDERX2, // Cavium ThunderX2 (originally Broadcom Vulkan).
@@ -155,8 +158,10 @@ static const ISA isas_uarch[] = {
[UARCH_EXYNOS_M3] = ISA_ARMv8_A, [UARCH_EXYNOS_M3] = ISA_ARMv8_A,
[UARCH_EXYNOS_M4] = ISA_ARMv8_2_A, [UARCH_EXYNOS_M4] = ISA_ARMv8_2_A,
[UARCH_EXYNOS_M5] = ISA_ARMv8_2_A, [UARCH_EXYNOS_M5] = ISA_ARMv8_2_A,
[UARCH_ICESTORM] = ISA_ARMv8_4_A, [UARCH_ICESTORM] = ISA_ARMv8_5_A, // https://github.com/llvm/llvm-project/blob/main/llvm/include/llvm/Support/AArch64TargetParser.def
[UARCH_FIRESTORM] = ISA_ARMv8_4_A, [UARCH_FIRESTORM] = ISA_ARMv8_5_A,
[UARCH_BLIZZARD] = ISA_ARMv8_5_A, // Not confirmed
[UARCH_AVALANCHE] = ISA_ARMv8_5_A,
[UARCH_PJ4] = ISA_ARMv7_A, [UARCH_PJ4] = ISA_ARMv7_A,
[UARCH_XIAOMI] = ISA_ARMv8_A, [UARCH_XIAOMI] = ISA_ARMv8_A,
}; };
@@ -172,7 +177,8 @@ static char* isas_string[] = {
[ISA_ARMv8_1_A] = "ARMv8.1", [ISA_ARMv8_1_A] = "ARMv8.1",
[ISA_ARMv8_2_A] = "ARMv8.2", [ISA_ARMv8_2_A] = "ARMv8.2",
[ISA_ARMv8_3_A] = "ARMv8.3", [ISA_ARMv8_3_A] = "ARMv8.3",
[ISA_ARMv8_4_A] = "ARMv8.4" [ISA_ARMv8_4_A] = "ARMv8.4",
[ISA_ARMv8_5_A] = "ARMv8.5"
}; };
#define UARCH_START if (false) {} #define UARCH_START if (false) {}
@@ -297,6 +303,8 @@ struct uarch* get_uarch_from_midr(uint32_t midr, struct cpuInfo* cpu) {
CHECK_UARCH(arch, cpu, 'a', 0x022, NA, NA, "Icestorm", UARCH_ICESTORM, CPU_VENDOR_APPLE) CHECK_UARCH(arch, cpu, 'a', 0x022, NA, NA, "Icestorm", UARCH_ICESTORM, CPU_VENDOR_APPLE)
CHECK_UARCH(arch, cpu, 'a', 0x023, NA, NA, "Firestorm", UARCH_FIRESTORM, CPU_VENDOR_APPLE) CHECK_UARCH(arch, cpu, 'a', 0x023, NA, NA, "Firestorm", UARCH_FIRESTORM, CPU_VENDOR_APPLE)
CHECK_UARCH(arch, cpu, 'a', 0x030, NA, NA, "Blizzard", UARCH_BLIZZARD, CPU_VENDOR_APPLE)
CHECK_UARCH(arch, cpu, 'a', 0x031, NA, NA, "Avalanche", UARCH_AVALANCHE, CPU_VENDOR_APPLE)
CHECK_UARCH(arch, cpu, 'V', 0x581, NA, NA, "PJ4", UARCH_PJ4, CPU_VENDOR_MARVELL) CHECK_UARCH(arch, cpu, 'V', 0x581, NA, NA, "PJ4", UARCH_PJ4, CPU_VENDOR_MARVELL)
CHECK_UARCH(arch, cpu, 'V', 0x584, NA, NA, "PJ4B-MP", UARCH_PJ4, CPU_VENDOR_MARVELL) CHECK_UARCH(arch, cpu, 'V', 0x584, NA, NA, "PJ4B-MP", UARCH_PJ4, CPU_VENDOR_MARVELL)

View File

@@ -166,7 +166,6 @@ long get_l3_cache_size(uint32_t core) {
} }
int get_num_caches_from_files(char** paths, int num_paths) { int get_num_caches_from_files(char** paths, int num_paths) {
int SHARED_MAP_MAX_LEN = 8 + 1;
int filelen; int filelen;
char* buf; char* buf;
uint32_t* shared_maps = emalloc(sizeof(uint32_t *) * num_paths); uint32_t* shared_maps = emalloc(sizeof(uint32_t *) * num_paths);
@@ -178,11 +177,6 @@ int get_num_caches_from_files(char** paths, int num_paths) {
return -1; return -1;
} }
if(filelen > SHARED_MAP_MAX_LEN) {
printBug("Shared map length is %d while the max is be %d", filelen, SHARED_MAP_MAX_LEN);
return -1;
}
char* end; char* end;
errno = 0; errno = 0;
long ret = strtol(buf, &end, 16); long ret = strtol(buf, &end, 16);