mirror of
https://github.com/Dr-Noob/cpufetch.git
synced 2026-03-25 07:50:40 +01:00
[v0.8][ARM] Building support in ARM
This commit is contained in:
26
Makefile
26
Makefile
@@ -3,15 +3,29 @@ CXX=gcc
|
|||||||
CXXFLAGS=-Wall -Wextra -Werror -pedantic -fstack-protector-all -pedantic -std=c99
|
CXXFLAGS=-Wall -Wextra -Werror -pedantic -fstack-protector-all -pedantic -std=c99
|
||||||
SANITY_FLAGS=-Wfloat-equal -Wshadow -Wpointer-arith -Wstrict-overflow=5 -Wformat=2
|
SANITY_FLAGS=-Wfloat-equal -Wshadow -Wpointer-arith -Wstrict-overflow=5 -Wformat=2
|
||||||
|
|
||||||
SRC_DIR=src/
|
COMMON_DIR=src/common/
|
||||||
SOURCE=$(SRC_DIR)main.c $(SRC_DIR)cpuid.c $(SRC_DIR)apic.c $(SRC_DIR)cpuid_asm.c $(SRC_DIR)printer.c $(SRC_DIR)args.c $(SRC_DIR)global.c $(SRC_DIR)uarch.c
|
|
||||||
HEADERS=$(SRC_DIR)cpuid.h $(SRC_DIR)apic.h $(SRC_DIR)cpuid_asm.h $(SRC_DIR)printer.h $(SRC_DIR)ascii.h $(SRC_DIR)args.h $(SRC_DIR)global.h $(SRC_DIR)uarch.h
|
|
||||||
|
|
||||||
ifneq ($(OS),Windows_NT)
|
ifneq ($(OS),Windows_NT)
|
||||||
SOURCE += $(SRC_DIR)udev.c
|
arch := $(shell uname -m)
|
||||||
HEADERS += $(SRC_DIR)udev.h
|
ifeq ($(arch), x86_64)
|
||||||
|
SRC_DIR=src/x86/
|
||||||
|
SOURCE += $(COMMON_DIR)main.c $(SRC_DIR)cpuid.c $(SRC_DIR)apic.c $(SRC_DIR)cpuid_asm.c $(SRC_DIR)udev.c $(SRC_DIR)uarch.c $(COMMON_DIR)printer.c $(COMMON_DIR)args.c $(COMMON_DIR)global.c
|
||||||
|
HEADERS += $(SRC_DIR)cpuid.h $(SRC_DIR)apic.h $(SRC_DIR)cpuid_asm.h $(SRC_DIR)udev.h $(SRC_DIR)uarch.h $(COMMON_DIR)ascii.h $(COMMON_DIR)printer.h $(COMMON_DIR)args.h $(COMMON_DIR)global.h
|
||||||
|
CXXFLAGS += -D_ARCH_X86
|
||||||
|
else
|
||||||
|
SRC_DIR=src/arm/
|
||||||
|
SOURCE += $(COMMON_DIR)main.c $(SRC_DIR)cpuid.c $(SRC_DIR)uarch.c $(COMMON_DIR)printer.c $(COMMON_DIR)args.c $(COMMON_DIR)global.c
|
||||||
|
HEADERS += $(COMMON_DIR)ascii.h $(SRC_DIR)uarch.h $(SRC_DIR)cpuid.h $(COMMON_DIR)printer.h $(COMMON_DIR)args.h $(COMMON_DIR)global.h
|
||||||
|
CXXFLAGS += -D_ARCH_ARM -Wno-unused-parameter
|
||||||
|
endif
|
||||||
|
|
||||||
OUTPUT=cpufetch
|
OUTPUT=cpufetch
|
||||||
else
|
else
|
||||||
|
# Assume x86_64
|
||||||
|
SRC_DIR=src/x86/
|
||||||
|
SOURCE += $(COMMON_DIR)main.c $(SRC_DIR)cpuid.c $(SRC_DIR)apic.c $(SRC_DIR)cpuid_asm.c $(SRC_DIR)udev.c $(SRC_DIR)uarch.c $(COMMON_DIR)printer.c $(COMMON_DIR)args.c $(COMMON_DIR)global.c
|
||||||
|
HEADERS += $(SRC_DIR)cpuid.h $(SRC_DIR)apic.h $(SRC_DIR)cpuid_asm.h $(SRC_DIR)udev.h $(SRC_DIR)uarch.h $(COMMON_DIR)ascii.h $(COMMON_DIR)printer.h $(COMMON_DIR)args.h $(COMMON_DIR)global.h
|
||||||
|
CXXFLAGS += -D_ARCH_X86
|
||||||
SANITY_FLAGS += -Wno-pedantic-ms-format
|
SANITY_FLAGS += -Wno-pedantic-ms-format
|
||||||
OUTPUT=cpufetch.exe
|
OUTPUT=cpufetch.exe
|
||||||
endif
|
endif
|
||||||
@@ -27,7 +41,7 @@ release: $(OUTPUT)
|
|||||||
$(OUTPUT): Makefile $(SOURCE) $(HEADERS)
|
$(OUTPUT): Makefile $(SOURCE) $(HEADERS)
|
||||||
$(CXX) $(CXXFLAGS) $(SANITY_FLAGS) $(SOURCE) -o $(OUTPUT)
|
$(CXX) $(CXXFLAGS) $(SANITY_FLAGS) $(SOURCE) -o $(OUTPUT)
|
||||||
|
|
||||||
run:
|
run: $(OUTPUT)
|
||||||
./$(OUTPUT)
|
./$(OUTPUT)
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
|
|||||||
112
src/arm/cpuid.c
Normal file
112
src/arm/cpuid.c
Normal file
@@ -0,0 +1,112 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <assert.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
#include "cpuid.h"
|
||||||
|
|
||||||
|
struct frequency {
|
||||||
|
int64_t base;
|
||||||
|
int64_t max;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct cpuInfo* get_cpu_info() {
|
||||||
|
struct cpuInfo* cpu = malloc(sizeof(struct cpuInfo));
|
||||||
|
|
||||||
|
cpu->cpu_vendor = CPU_VENDOR_UNKNOWN;
|
||||||
|
cpu->cpu_name = malloc(sizeof(char) * CPU_NAME_MAX_LENGTH);
|
||||||
|
strcpy(cpu->cpu_name, "Unknown");
|
||||||
|
cpu->arch = NULL;
|
||||||
|
cpu->hv = malloc(sizeof(struct hypervisor));
|
||||||
|
cpu->hv->present = false;
|
||||||
|
|
||||||
|
return cpu;
|
||||||
|
}
|
||||||
|
|
||||||
|
void init_topology_struct(struct topology* topo, struct cache* cach) {
|
||||||
|
topo->total_cores = 0;
|
||||||
|
topo->physical_cores = 0;
|
||||||
|
topo->logical_cores = 0;
|
||||||
|
topo->smt_available = 0;
|
||||||
|
topo->smt_supported = 0;
|
||||||
|
topo->sockets = 0;
|
||||||
|
topo->cach = cach;
|
||||||
|
}
|
||||||
|
|
||||||
|
void init_cache_struct(struct cache* cach) {
|
||||||
|
cach->L1i = malloc(sizeof(struct cach));
|
||||||
|
cach->L1d = malloc(sizeof(struct cach));
|
||||||
|
cach->L2 = malloc(sizeof(struct cach));
|
||||||
|
cach->L3 = malloc(sizeof(struct cach));
|
||||||
|
|
||||||
|
cach->cach_arr = malloc(sizeof(struct cach*) * 4);
|
||||||
|
cach->cach_arr[0] = cach->L1i;
|
||||||
|
cach->cach_arr[1] = cach->L1d;
|
||||||
|
cach->cach_arr[2] = cach->L2;
|
||||||
|
cach->cach_arr[3] = cach->L3;
|
||||||
|
|
||||||
|
cach->max_cache_level = 0;
|
||||||
|
cach->L1i->exists = false;
|
||||||
|
cach->L1d->exists = false;
|
||||||
|
cach->L2->exists = false;
|
||||||
|
cach->L3->exists = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct cache* get_cache_info(struct cpuInfo* cpu) {
|
||||||
|
struct cache* cach = malloc(sizeof(struct cache));
|
||||||
|
init_cache_struct(cach);
|
||||||
|
return cach;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct frequency* get_frequency_info(struct cpuInfo* cpu) {
|
||||||
|
struct frequency* freq = malloc(sizeof(struct frequency));
|
||||||
|
|
||||||
|
freq->base = UNKNOWN_FREQ;
|
||||||
|
freq->max = UNKNOWN_FREQ;
|
||||||
|
|
||||||
|
return freq;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct topology* get_topology_info(struct cpuInfo* cpu, struct cache* cach) {
|
||||||
|
struct topology* topo = malloc(sizeof(struct topology));
|
||||||
|
init_topology_struct(topo, cach);
|
||||||
|
return topo;
|
||||||
|
}
|
||||||
|
|
||||||
|
VENDOR get_cpu_vendor(struct cpuInfo* cpu) {
|
||||||
|
return cpu->cpu_vendor;
|
||||||
|
}
|
||||||
|
uint32_t get_nsockets(struct topology* topo) { return 0; }
|
||||||
|
int64_t get_freq(struct frequency* freq) { return 0; }
|
||||||
|
|
||||||
|
char* get_str_cpu_name(struct cpuInfo* cpu) {
|
||||||
|
return cpu->cpu_name;
|
||||||
|
}
|
||||||
|
char* get_str_ncores(struct cpuInfo* cpu){ return NULL; }
|
||||||
|
char* get_str_avx(struct cpuInfo* cpu){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "No"); return tmp; }
|
||||||
|
char* get_str_sse(struct cpuInfo* cpu){ return NULL; }
|
||||||
|
char* get_str_fma(struct cpuInfo* cpu){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "No"); return tmp; }
|
||||||
|
char* get_str_aes(struct cpuInfo* cpu){ return NULL; }
|
||||||
|
char* get_str_sha(struct cpuInfo* cpu){ return NULL; }
|
||||||
|
|
||||||
|
char* get_str_l1i(struct cache* cach){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 KB"); return tmp; }
|
||||||
|
char* get_str_l1d(struct cache* cach){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 KB"); return tmp; }
|
||||||
|
char* get_str_l2(struct cache* cach){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 KB"); return tmp; }
|
||||||
|
char* get_str_l3(struct cache* cach){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 KB"); return tmp; }
|
||||||
|
|
||||||
|
char* get_str_freq(struct frequency* freq){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 MHz"); return tmp; }
|
||||||
|
|
||||||
|
char* get_str_sockets(struct topology* topo){ return NULL; }
|
||||||
|
char* get_str_topology(struct cpuInfo* cpu, struct topology* topo, bool dual_socket){ char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 cores"); return tmp; }
|
||||||
|
|
||||||
|
char* get_str_peak_performance(struct cpuInfo* cpu, struct topology* topo, int64_t freq) { char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "0 MFLOP/s"); return tmp; }
|
||||||
|
|
||||||
|
void free_cache_struct(struct cache* cach){ }
|
||||||
|
void free_topo_struct(struct topology* topo){ }
|
||||||
|
void free_freq_struct(struct frequency* freq){ }
|
||||||
|
void free_cpuinfo_struct(struct cpuInfo* cpu){ }
|
||||||
|
|
||||||
|
void debug_cpu_info(struct cpuInfo* cpu){ }
|
||||||
|
void debug_cache(struct cache* cach){ }
|
||||||
|
void debug_frequency(struct frequency* freq){ }
|
||||||
44
src/arm/cpuid.h
Normal file
44
src/arm/cpuid.h
Normal file
@@ -0,0 +1,44 @@
|
|||||||
|
#ifndef __CPUID__
|
||||||
|
#define __CPUID__
|
||||||
|
|
||||||
|
#include "../common/cpu.h"
|
||||||
|
|
||||||
|
struct cpuInfo* get_cpu_info();
|
||||||
|
struct cache* get_cache_info(struct cpuInfo* cpu);
|
||||||
|
struct frequency* get_frequency_info(struct cpuInfo* cpu);
|
||||||
|
struct topology* get_topology_info(struct cpuInfo* cpu, struct cache* cach);
|
||||||
|
|
||||||
|
VENDOR get_cpu_vendor(struct cpuInfo* cpu);
|
||||||
|
uint32_t get_nsockets(struct topology* topo);
|
||||||
|
int64_t get_freq(struct frequency* freq);
|
||||||
|
|
||||||
|
char* get_str_cpu_name(struct cpuInfo* cpu);
|
||||||
|
char* get_str_ncores(struct cpuInfo* cpu);
|
||||||
|
char* get_str_avx(struct cpuInfo* cpu);
|
||||||
|
char* get_str_sse(struct cpuInfo* cpu);
|
||||||
|
char* get_str_fma(struct cpuInfo* cpu);
|
||||||
|
char* get_str_aes(struct cpuInfo* cpu);
|
||||||
|
char* get_str_sha(struct cpuInfo* cpu);
|
||||||
|
|
||||||
|
char* get_str_l1i(struct cache* cach);
|
||||||
|
char* get_str_l1d(struct cache* cach);
|
||||||
|
char* get_str_l2(struct cache* cach);
|
||||||
|
char* get_str_l3(struct cache* cach);
|
||||||
|
|
||||||
|
char* get_str_freq(struct frequency* freq);
|
||||||
|
|
||||||
|
char* get_str_sockets(struct topology* topo);
|
||||||
|
char* get_str_topology(struct cpuInfo* cpu, struct topology* topo, bool dual_socket);
|
||||||
|
|
||||||
|
char* get_str_peak_performance(struct cpuInfo* cpu, struct topology* topo, int64_t freq);
|
||||||
|
|
||||||
|
void free_cache_struct(struct cache* cach);
|
||||||
|
void free_topo_struct(struct topology* topo);
|
||||||
|
void free_freq_struct(struct frequency* freq);
|
||||||
|
void free_cpuinfo_struct(struct cpuInfo* cpu);
|
||||||
|
|
||||||
|
void debug_cpu_info(struct cpuInfo* cpu);
|
||||||
|
void debug_cache(struct cache* cach);
|
||||||
|
void debug_frequency(struct frequency* freq);
|
||||||
|
|
||||||
|
#endif
|
||||||
15
src/arm/uarch.c
Normal file
15
src/arm/uarch.c
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
#include <stdbool.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include "uarch.h"
|
||||||
|
#include "../common/global.h"
|
||||||
|
|
||||||
|
struct uarch* get_uarch_from_cpuid(struct cpuInfo* cpu, uint32_t ef, uint32_t f, uint32_t em, uint32_t m, int s) { return NULL; }
|
||||||
|
bool vpus_are_AVX512(struct cpuInfo* cpu) { return false; }
|
||||||
|
bool is_knights_landing(struct cpuInfo* cpu) { return false; }
|
||||||
|
int get_number_of_vpus(struct cpuInfo* cpu) { return 0; }
|
||||||
|
char* get_str_uarch(struct cpuInfo* cpu) { char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "Unknown"); return tmp; }
|
||||||
|
char* get_str_process(struct cpuInfo* cpu) { char* tmp = malloc(sizeof(char) * 10); strcpy(tmp, "Unknown"); return tmp; }
|
||||||
|
void free_uarch_struct(struct uarch* arch) { }
|
||||||
@@ -46,4 +46,25 @@
|
|||||||
########## ################ \
|
########## ################ \
|
||||||
############################### "
|
############################### "
|
||||||
|
|
||||||
|
#define UNKNOWN_ASCII \
|
||||||
|
" \
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
\
|
||||||
|
"
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
95
src/common/cpu.h
Normal file
95
src/common/cpu.h
Normal file
@@ -0,0 +1,95 @@
|
|||||||
|
#ifndef __CPU__
|
||||||
|
#define __CPU__
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
enum {
|
||||||
|
CPU_VENDOR_INTEL,
|
||||||
|
CPU_VENDOR_AMD,
|
||||||
|
CPU_VENDOR_UNKNOWN,
|
||||||
|
CPU_VENDOR_INVALID
|
||||||
|
};
|
||||||
|
|
||||||
|
enum {
|
||||||
|
HV_VENDOR_KVM,
|
||||||
|
HV_VENDOR_QEMU,
|
||||||
|
HV_VENDOR_HYPERV,
|
||||||
|
HV_VENDOR_VMWARE,
|
||||||
|
HV_VENDOR_XEN,
|
||||||
|
HV_VENDOR_PARALLELS,
|
||||||
|
HV_VENDOR_INVALID
|
||||||
|
};
|
||||||
|
|
||||||
|
#define UNKNOWN_FREQ -1
|
||||||
|
#define CPU_NAME_MAX_LENGTH 64
|
||||||
|
|
||||||
|
typedef int32_t VENDOR;
|
||||||
|
|
||||||
|
struct frequency;
|
||||||
|
|
||||||
|
struct hypervisor {
|
||||||
|
bool present;
|
||||||
|
char* hv_name;
|
||||||
|
VENDOR hv_vendor;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct cpuInfo {
|
||||||
|
bool AVX;
|
||||||
|
bool AVX2;
|
||||||
|
bool AVX512;
|
||||||
|
bool SSE;
|
||||||
|
bool SSE2;
|
||||||
|
bool SSE3;
|
||||||
|
bool SSSE3;
|
||||||
|
bool SSE4a;
|
||||||
|
bool SSE4_1;
|
||||||
|
bool SSE4_2;
|
||||||
|
bool FMA3;
|
||||||
|
bool FMA4;
|
||||||
|
bool AES;
|
||||||
|
bool SHA;
|
||||||
|
|
||||||
|
VENDOR cpu_vendor;
|
||||||
|
|
||||||
|
char* cpu_name;
|
||||||
|
// Max cpuids levels
|
||||||
|
uint32_t maxLevels;
|
||||||
|
// Max cpuids extended levels
|
||||||
|
uint32_t maxExtendedLevels;
|
||||||
|
|
||||||
|
struct uarch* arch;
|
||||||
|
struct hypervisor* hv;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct cach {
|
||||||
|
int32_t size;
|
||||||
|
uint8_t num_caches;
|
||||||
|
bool exists;
|
||||||
|
// plenty of more properties to include in the future...
|
||||||
|
};
|
||||||
|
|
||||||
|
struct cache {
|
||||||
|
struct cach* L1i;
|
||||||
|
struct cach* L1d;
|
||||||
|
struct cach* L2;
|
||||||
|
struct cach* L3;
|
||||||
|
struct cach** cach_arr;
|
||||||
|
|
||||||
|
uint8_t max_cache_level;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct topology {
|
||||||
|
int64_t total_cores;
|
||||||
|
uint32_t physical_cores;
|
||||||
|
uint32_t logical_cores;
|
||||||
|
uint32_t smt_available; // Number of SMT that is currently enabled
|
||||||
|
uint32_t smt_supported; // Number of SMT that CPU supports (equal to smt_available if SMT is enabled)
|
||||||
|
uint32_t sockets;
|
||||||
|
struct cache* cach;
|
||||||
|
#ifdef _ARCH_X86
|
||||||
|
struct apic* apic;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -3,10 +3,17 @@
|
|||||||
|
|
||||||
#include "args.h"
|
#include "args.h"
|
||||||
#include "printer.h"
|
#include "printer.h"
|
||||||
#include "cpuid.h"
|
|
||||||
#include "global.h"
|
#include "global.h"
|
||||||
|
|
||||||
static const char* VERSION = "0.72";
|
#ifdef _ARCH_X86
|
||||||
|
static const char* ARCH_STR = "x86_64 build";
|
||||||
|
#include "../x86/cpuid.h"
|
||||||
|
#else
|
||||||
|
static const char* ARCH_STR = "ARM build";
|
||||||
|
#include "../arm/cpuid.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static const char* VERSION = "0.8";
|
||||||
|
|
||||||
void print_help(char *argv[]) {
|
void print_help(char *argv[]) {
|
||||||
printf("Usage: %s [--version] [--help] [--levels] [--style \"fancy\"|\"retro\"|\"legacy\"] [--color \"intel\"|\"amd\"|'R,G,B:R,G,B:R,G,B:R,G,B']\n\n\
|
printf("Usage: %s [--version] [--help] [--levels] [--style \"fancy\"|\"retro\"|\"legacy\"] [--color \"intel\"|\"amd\"|'R,G,B:R,G,B:R,G,B:R,G,B']\n\n\
|
||||||
@@ -37,7 +44,7 @@ NOTES: \n\
|
|||||||
}
|
}
|
||||||
|
|
||||||
void print_version() {
|
void print_version() {
|
||||||
printf("cpufetch v%s\n",VERSION);
|
printf("cpufetch v%s (%s)\n",VERSION, ARCH_STR);
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char* argv[]) {
|
int main(int argc, char* argv[]) {
|
||||||
@@ -5,29 +5,40 @@
|
|||||||
|
|
||||||
#include "printer.h"
|
#include "printer.h"
|
||||||
#include "ascii.h"
|
#include "ascii.h"
|
||||||
#include "global.h"
|
#include "../common/global.h"
|
||||||
#include "cpuid.h"
|
|
||||||
#include "uarch.h"
|
#ifdef _ARCH_X86
|
||||||
|
#include "../x86/uarch.h"
|
||||||
|
#include "../x86/cpuid.h"
|
||||||
|
#else
|
||||||
|
#include "../arm/cpuid.h"
|
||||||
|
#include "../arm/uarch.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
#define NOMINMAX
|
#define NOMINMAX
|
||||||
#include <Windows.h>
|
#include <Windows.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define COL_NONE ""
|
#define COL_NONE ""
|
||||||
#define COL_INTEL_FANCY_1 "\x1b[46;1m"
|
#define COL_INTEL_FANCY_1 "\x1b[46;1m"
|
||||||
#define COL_INTEL_FANCY_2 "\x1b[47;1m"
|
#define COL_INTEL_FANCY_2 "\x1b[47;1m"
|
||||||
#define COL_INTEL_FANCY_3 "\x1b[36;1m"
|
#define COL_INTEL_FANCY_3 "\x1b[36;1m"
|
||||||
#define COL_INTEL_FANCY_4 "\x1b[37;1m"
|
#define COL_INTEL_FANCY_4 "\x1b[37;1m"
|
||||||
#define COL_INTEL_RETRO_1 "\x1b[36;1m"
|
#define COL_INTEL_RETRO_1 "\x1b[36;1m"
|
||||||
#define COL_INTEL_RETRO_2 "\x1b[37;1m"
|
#define COL_INTEL_RETRO_2 "\x1b[37;1m"
|
||||||
#define COL_AMD_FANCY_1 "\x1b[47;1m"
|
#define COL_AMD_FANCY_1 "\x1b[47;1m"
|
||||||
#define COL_AMD_FANCY_2 "\x1b[42;1m"
|
#define COL_AMD_FANCY_2 "\x1b[42;1m"
|
||||||
#define COL_AMD_FANCY_3 "\x1b[37;1m"
|
#define COL_AMD_FANCY_3 "\x1b[37;1m"
|
||||||
#define COL_AMD_FANCY_4 "\x1b[32;1m"
|
#define COL_AMD_FANCY_4 "\x1b[32;1m"
|
||||||
#define COL_AMD_RETRO_1 "\x1b[37;1m"
|
#define COL_AMD_RETRO_1 "\x1b[37;1m"
|
||||||
#define COL_AMD_RETRO_2 "\x1b[32;1m"
|
#define COL_AMD_RETRO_2 "\x1b[32;1m"
|
||||||
#define RESET "\x1b[m"
|
#define COL_UNKNOWN_FANCY_1 "\x1b[47;1m"
|
||||||
|
#define COL_UNKNOWN_FANCY_2 "\x1b[47;1m"
|
||||||
|
#define COL_UNKNOWN_FANCY_3 "\x1b[37;1m"
|
||||||
|
#define COL_UNKNOWN_FANCY_4 "\x1b[31;1m"
|
||||||
|
#define COL_UNKNOWN_RETRO "\x1b[32;0m"
|
||||||
|
#define RESET "\x1b[m"
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
ATTRIBUTE_NAME,
|
ATTRIBUTE_NAME,
|
||||||
@@ -153,7 +164,7 @@ struct ascii* set_ascii(VENDOR cpuVendor, STYLE style, struct colors* cs) {
|
|||||||
COL_RETRO_4 = COL_INTEL_RETRO_2;
|
COL_RETRO_4 = COL_INTEL_RETRO_2;
|
||||||
art->ascii_chars[0] = '#';
|
art->ascii_chars[0] = '#';
|
||||||
}
|
}
|
||||||
else {
|
else if(art->vendor == CPU_VENDOR_AMD) {
|
||||||
COL_FANCY_1 = COL_AMD_FANCY_1;
|
COL_FANCY_1 = COL_AMD_FANCY_1;
|
||||||
COL_FANCY_2 = COL_AMD_FANCY_2;
|
COL_FANCY_2 = COL_AMD_FANCY_2;
|
||||||
COL_FANCY_3 = COL_AMD_FANCY_3;
|
COL_FANCY_3 = COL_AMD_FANCY_3;
|
||||||
@@ -164,6 +175,17 @@ struct ascii* set_ascii(VENDOR cpuVendor, STYLE style, struct colors* cs) {
|
|||||||
COL_RETRO_4 = COL_AMD_RETRO_2;
|
COL_RETRO_4 = COL_AMD_RETRO_2;
|
||||||
art->ascii_chars[0] = '@';
|
art->ascii_chars[0] = '@';
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
|
COL_FANCY_1 = COL_UNKNOWN_FANCY_1;
|
||||||
|
COL_FANCY_2 = COL_UNKNOWN_FANCY_2;
|
||||||
|
COL_FANCY_3 = COL_UNKNOWN_FANCY_3;
|
||||||
|
COL_FANCY_4 = COL_UNKNOWN_FANCY_4;
|
||||||
|
COL_RETRO_1 = COL_UNKNOWN_RETRO;
|
||||||
|
COL_RETRO_2 = COL_UNKNOWN_RETRO;
|
||||||
|
COL_RETRO_3 = COL_UNKNOWN_RETRO;
|
||||||
|
COL_RETRO_4 = COL_UNKNOWN_RETRO;
|
||||||
|
art->ascii_chars[0] = '#';
|
||||||
|
}
|
||||||
art->ascii_chars[1] = '#';
|
art->ascii_chars[1] = '#';
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
@@ -245,8 +267,10 @@ struct ascii* set_ascii(VENDOR cpuVendor, STYLE style, struct colors* cs) {
|
|||||||
char tmp[NUMBER_OF_LINES*LINE_SIZE];
|
char tmp[NUMBER_OF_LINES*LINE_SIZE];
|
||||||
if(art->vendor == CPU_VENDOR_INTEL)
|
if(art->vendor == CPU_VENDOR_INTEL)
|
||||||
strcpy(tmp, INTEL_ASCII);
|
strcpy(tmp, INTEL_ASCII);
|
||||||
else
|
else if(art->vendor == CPU_VENDOR_AMD)
|
||||||
strcpy(tmp, AMD_ASCII);
|
strcpy(tmp, AMD_ASCII);
|
||||||
|
else
|
||||||
|
strcpy(tmp, UNKNOWN_ASCII);
|
||||||
|
|
||||||
for(int i=0; i < NUMBER_OF_LINES; i++)
|
for(int i=0; i < NUMBER_OF_LINES; i++)
|
||||||
strncpy(art->art[i], tmp + i*LINE_SIZE, LINE_SIZE);
|
strncpy(art->art[i], tmp + i*LINE_SIZE, LINE_SIZE);
|
||||||
@@ -423,3 +447,11 @@ bool print_cpufetch(struct cpuInfo* cpu, struct cache* cach, struct frequency* f
|
|||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void print_levels(struct cpuInfo* cpu) {
|
||||||
|
printf("%s\n", cpu->cpu_name);
|
||||||
|
printf("- Max standart level: 0x%.8X\n", cpu->maxLevels);
|
||||||
|
printf("- Max extended level: 0x%.8X\n", cpu->maxExtendedLevels);
|
||||||
|
|
||||||
|
free_cpuinfo_struct(cpu);
|
||||||
|
}
|
||||||
@@ -4,11 +4,17 @@
|
|||||||
typedef int STYLE;
|
typedef int STYLE;
|
||||||
|
|
||||||
#include "args.h"
|
#include "args.h"
|
||||||
#include "cpuid.h"
|
|
||||||
|
#ifdef _ARCH_X86
|
||||||
|
#include "../x86/cpuid.h"
|
||||||
|
#else
|
||||||
|
#include "../arm/cpuid.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
#define COLOR_DEFAULT_INTEL "15,125,194:230,230,230:40,150,220:230,230,230"
|
#define COLOR_DEFAULT_INTEL "15,125,194:230,230,230:40,150,220:230,230,230"
|
||||||
#define COLOR_DEFAULT_AMD "250,250,250:0,154,102:250,250,250:0,154,102"
|
#define COLOR_DEFAULT_AMD "250,250,250:0,154,102:250,250,250:0,154,102"
|
||||||
|
|
||||||
|
void print_levels(struct cpuInfo* cpu);
|
||||||
bool print_cpufetch(struct cpuInfo* cpu, struct cache* cach, struct frequency* freq, struct topology* topo, STYLE s, struct colors* cs);
|
bool print_cpufetch(struct cpuInfo* cpu, struct cache* cach, struct frequency* freq, struct topology* topo, STYLE s, struct colors* cs);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
129
src/cpuid.h
129
src/cpuid.h
@@ -1,129 +0,0 @@
|
|||||||
#ifndef __CPUID__
|
|
||||||
#define __CPUID__
|
|
||||||
|
|
||||||
#include <stdint.h>
|
|
||||||
|
|
||||||
enum {
|
|
||||||
CPU_VENDOR_INTEL,
|
|
||||||
CPU_VENDOR_AMD,
|
|
||||||
CPU_VENDOR_INVALID
|
|
||||||
};
|
|
||||||
|
|
||||||
enum {
|
|
||||||
HV_VENDOR_KVM,
|
|
||||||
HV_VENDOR_QEMU,
|
|
||||||
HV_VENDOR_HYPERV,
|
|
||||||
HV_VENDOR_VMWARE,
|
|
||||||
HV_VENDOR_XEN,
|
|
||||||
HV_VENDOR_PARALLELS,
|
|
||||||
HV_VENDOR_INVALID
|
|
||||||
};
|
|
||||||
|
|
||||||
#define UNKNOWN_FREQ -1
|
|
||||||
|
|
||||||
typedef int32_t VENDOR;
|
|
||||||
|
|
||||||
struct frequency;
|
|
||||||
|
|
||||||
struct hypervisor {
|
|
||||||
bool present;
|
|
||||||
char* hv_name;
|
|
||||||
VENDOR hv_vendor;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct cpuInfo {
|
|
||||||
bool AVX;
|
|
||||||
bool AVX2;
|
|
||||||
bool AVX512;
|
|
||||||
bool SSE;
|
|
||||||
bool SSE2;
|
|
||||||
bool SSE3;
|
|
||||||
bool SSSE3;
|
|
||||||
bool SSE4a;
|
|
||||||
bool SSE4_1;
|
|
||||||
bool SSE4_2;
|
|
||||||
bool FMA3;
|
|
||||||
bool FMA4;
|
|
||||||
bool AES;
|
|
||||||
bool SHA;
|
|
||||||
|
|
||||||
VENDOR cpu_vendor;
|
|
||||||
|
|
||||||
char* cpu_name;
|
|
||||||
// Max cpuids levels
|
|
||||||
uint32_t maxLevels;
|
|
||||||
// Max cpuids extended levels
|
|
||||||
uint32_t maxExtendedLevels;
|
|
||||||
|
|
||||||
struct uarch* arch;
|
|
||||||
struct hypervisor* hv;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct cach {
|
|
||||||
int32_t size;
|
|
||||||
uint8_t num_caches;
|
|
||||||
bool exists;
|
|
||||||
// plenty of more properties to include in the future...
|
|
||||||
};
|
|
||||||
|
|
||||||
struct cache {
|
|
||||||
struct cach* L1i;
|
|
||||||
struct cach* L1d;
|
|
||||||
struct cach* L2;
|
|
||||||
struct cach* L3;
|
|
||||||
struct cach** cach_arr;
|
|
||||||
|
|
||||||
uint8_t max_cache_level;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct topology {
|
|
||||||
int64_t total_cores;
|
|
||||||
uint32_t physical_cores;
|
|
||||||
uint32_t logical_cores;
|
|
||||||
uint32_t smt_available; // Number of SMT that is currently enabled
|
|
||||||
uint32_t smt_supported; // Number of SMT that CPU supports (equal to smt_available if SMT is enabled)
|
|
||||||
uint32_t sockets;
|
|
||||||
struct apic* apic;
|
|
||||||
struct cache* cach;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct cpuInfo* get_cpu_info();
|
|
||||||
VENDOR get_cpu_vendor(struct cpuInfo* cpu);
|
|
||||||
uint32_t get_nsockets(struct topology* topo);
|
|
||||||
int64_t get_freq(struct frequency* freq);
|
|
||||||
struct cache* get_cache_info(struct cpuInfo* cpu);
|
|
||||||
struct frequency* get_frequency_info(struct cpuInfo* cpu);
|
|
||||||
struct topology* get_topology_info(struct cpuInfo* cpu, struct cache* cach);
|
|
||||||
|
|
||||||
char* get_str_cpu_name(struct cpuInfo* cpu);
|
|
||||||
char* get_str_ncores(struct cpuInfo* cpu);
|
|
||||||
char* get_str_avx(struct cpuInfo* cpu);
|
|
||||||
char* get_str_sse(struct cpuInfo* cpu);
|
|
||||||
char* get_str_fma(struct cpuInfo* cpu);
|
|
||||||
char* get_str_aes(struct cpuInfo* cpu);
|
|
||||||
char* get_str_sha(struct cpuInfo* cpu);
|
|
||||||
|
|
||||||
char* get_str_l1i(struct cache* cach);
|
|
||||||
char* get_str_l1d(struct cache* cach);
|
|
||||||
char* get_str_l2(struct cache* cach);
|
|
||||||
char* get_str_l3(struct cache* cach);
|
|
||||||
|
|
||||||
char* get_str_freq(struct frequency* freq);
|
|
||||||
|
|
||||||
char* get_str_sockets(struct topology* topo);
|
|
||||||
char* get_str_topology(struct cpuInfo* cpu, struct topology* topo, bool dual_socket);
|
|
||||||
|
|
||||||
char* get_str_peak_performance(struct cpuInfo* cpu, struct topology* topo, int64_t freq);
|
|
||||||
|
|
||||||
void print_levels(struct cpuInfo* cpu);
|
|
||||||
|
|
||||||
void free_cache_struct(struct cache* cach);
|
|
||||||
void free_topo_struct(struct topology* topo);
|
|
||||||
void free_freq_struct(struct frequency* freq);
|
|
||||||
void free_cpuinfo_struct(struct cpuInfo* cpu);
|
|
||||||
|
|
||||||
void debug_cpu_info(struct cpuInfo* cpu);
|
|
||||||
void debug_cache(struct cache* cach);
|
|
||||||
void debug_frequency(struct frequency* freq);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
@@ -12,7 +12,7 @@
|
|||||||
|
|
||||||
#include "apic.h"
|
#include "apic.h"
|
||||||
#include "cpuid_asm.h"
|
#include "cpuid_asm.h"
|
||||||
#include "global.h"
|
#include "../common/global.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* bit_scan_reverse and create_mask code taken from:
|
* bit_scan_reverse and create_mask code taken from:
|
||||||
@@ -13,7 +13,7 @@
|
|||||||
|
|
||||||
#include "cpuid.h"
|
#include "cpuid.h"
|
||||||
#include "cpuid_asm.h"
|
#include "cpuid_asm.h"
|
||||||
#include "global.h"
|
#include "../common/global.h"
|
||||||
#include "apic.h"
|
#include "apic.h"
|
||||||
#include "uarch.h"
|
#include "uarch.h"
|
||||||
|
|
||||||
@@ -49,7 +49,6 @@ static char *hv_vendors_name[] = {
|
|||||||
#define STRING_KILOBYTES "KB"
|
#define STRING_KILOBYTES "KB"
|
||||||
#define STRING_MEGABYTES "MB"
|
#define STRING_MEGABYTES "MB"
|
||||||
|
|
||||||
#define CPU_NAME_MAX_LENGTH 64
|
|
||||||
#define HYPERVISOR_NAME_MAX_LENGTH 17
|
#define HYPERVISOR_NAME_MAX_LENGTH 17
|
||||||
|
|
||||||
#define MASK 0xFF
|
#define MASK 0xFF
|
||||||
@@ -1029,14 +1028,6 @@ char* get_str_freq(struct frequency* freq) {
|
|||||||
return string;
|
return string;
|
||||||
}
|
}
|
||||||
|
|
||||||
void print_levels(struct cpuInfo* cpu) {
|
|
||||||
printf("%s\n", cpu->cpu_name);
|
|
||||||
printf("- Max standart level: 0x%.8X\n", cpu->maxLevels);
|
|
||||||
printf("- Max extended level: 0x%.8X\n", cpu->maxExtendedLevels);
|
|
||||||
|
|
||||||
free_cpuinfo_struct(cpu);
|
|
||||||
}
|
|
||||||
|
|
||||||
void free_topo_struct(struct topology* topo) {
|
void free_topo_struct(struct topology* topo) {
|
||||||
free(topo->apic->cache_select_mask);
|
free(topo->apic->cache_select_mask);
|
||||||
free(topo->apic->cache_id_apic);
|
free(topo->apic->cache_id_apic);
|
||||||
44
src/x86/cpuid.h
Normal file
44
src/x86/cpuid.h
Normal file
@@ -0,0 +1,44 @@
|
|||||||
|
#ifndef __CPUID__
|
||||||
|
#define __CPUID__
|
||||||
|
|
||||||
|
#include "../common/cpu.h"
|
||||||
|
|
||||||
|
struct cpuInfo* get_cpu_info();
|
||||||
|
struct cache* get_cache_info(struct cpuInfo* cpu);
|
||||||
|
struct frequency* get_frequency_info(struct cpuInfo* cpu);
|
||||||
|
struct topology* get_topology_info(struct cpuInfo* cpu, struct cache* cach);
|
||||||
|
|
||||||
|
VENDOR get_cpu_vendor(struct cpuInfo* cpu);
|
||||||
|
uint32_t get_nsockets(struct topology* topo);
|
||||||
|
int64_t get_freq(struct frequency* freq);
|
||||||
|
|
||||||
|
char* get_str_cpu_name(struct cpuInfo* cpu);
|
||||||
|
char* get_str_ncores(struct cpuInfo* cpu);
|
||||||
|
char* get_str_avx(struct cpuInfo* cpu);
|
||||||
|
char* get_str_sse(struct cpuInfo* cpu);
|
||||||
|
char* get_str_fma(struct cpuInfo* cpu);
|
||||||
|
char* get_str_aes(struct cpuInfo* cpu);
|
||||||
|
char* get_str_sha(struct cpuInfo* cpu);
|
||||||
|
|
||||||
|
char* get_str_l1i(struct cache* cach);
|
||||||
|
char* get_str_l1d(struct cache* cach);
|
||||||
|
char* get_str_l2(struct cache* cach);
|
||||||
|
char* get_str_l3(struct cache* cach);
|
||||||
|
|
||||||
|
char* get_str_freq(struct frequency* freq);
|
||||||
|
|
||||||
|
char* get_str_sockets(struct topology* topo);
|
||||||
|
char* get_str_topology(struct cpuInfo* cpu, struct topology* topo, bool dual_socket);
|
||||||
|
|
||||||
|
char* get_str_peak_performance(struct cpuInfo* cpu, struct topology* topo, int64_t freq);
|
||||||
|
|
||||||
|
void free_cache_struct(struct cache* cach);
|
||||||
|
void free_topo_struct(struct topology* topo);
|
||||||
|
void free_freq_struct(struct frequency* freq);
|
||||||
|
void free_cpuinfo_struct(struct cpuInfo* cpu);
|
||||||
|
|
||||||
|
void debug_cpu_info(struct cpuInfo* cpu);
|
||||||
|
void debug_cache(struct cache* cach);
|
||||||
|
void debug_frequency(struct frequency* freq);
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -4,7 +4,7 @@
|
|||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "uarch.h"
|
#include "uarch.h"
|
||||||
#include "global.h"
|
#include "../common/global.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* - cpuid codes are based on Todd Allen's cpuid program
|
* - cpuid codes are based on Todd Allen's cpuid program
|
||||||
18
src/x86/uarch.h
Normal file
18
src/x86/uarch.h
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
#ifndef __UARCH__
|
||||||
|
#define __UARCH__
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
#include "cpuid.h"
|
||||||
|
|
||||||
|
struct uarch;
|
||||||
|
|
||||||
|
struct uarch* get_uarch_from_cpuid(struct cpuInfo* cpu, uint32_t ef, uint32_t f, uint32_t em, uint32_t m, int s);
|
||||||
|
bool vpus_are_AVX512(struct cpuInfo* cpu);
|
||||||
|
bool is_knights_landing(struct cpuInfo* cpu);
|
||||||
|
int get_number_of_vpus(struct cpuInfo* cpu);
|
||||||
|
char* get_str_uarch(struct cpuInfo* cpu);
|
||||||
|
char* get_str_process(struct cpuInfo* cpu);
|
||||||
|
void free_uarch_struct(struct uarch* arch);
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -5,7 +5,7 @@
|
|||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|
||||||
#include "global.h"
|
#include "../common/global.h"
|
||||||
#include "cpuid.h"
|
#include "cpuid.h"
|
||||||
|
|
||||||
#define _PATH_SYS_SYSTEM "/sys/devices/system"
|
#define _PATH_SYS_SYSTEM "/sys/devices/system"
|
||||||
Reference in New Issue
Block a user