1
0
Fork 0
mirror of https://github.com/anrieff/libcpuid synced 2024-11-10 22:59:13 +00:00

Add Hygon Dhyana detect support

Signed-off-by: hygonsoc <hygonsoc@gmail.com>
This commit is contained in:
hygonsoc 2019-04-13 23:08:03 +08:00
parent 1168b8dd68
commit 8c0a01890c
6 changed files with 27 additions and 6 deletions

View file

@ -264,6 +264,7 @@ static cpu_vendor_t cpuid_vendor_identify(const uint32_t *raw_vendor, char *vend
{ VENDOR_RISE , "RiseRiseRise" }, { VENDOR_RISE , "RiseRiseRise" },
{ VENDOR_SIS , "SiS SiS SiS " }, { VENDOR_SIS , "SiS SiS SiS " },
{ VENDOR_NSC , "Geode by NSC" }, { VENDOR_NSC , "Geode by NSC" },
{ VENDOR_HYGON , "HygonGenuine" },
}; };
memcpy(vendor_str + 0, &raw_vendor[1], 4); memcpy(vendor_str + 0, &raw_vendor[1], 4);
@ -519,6 +520,7 @@ int cpu_ident_internal(struct cpu_raw_data_t* raw, struct cpu_id_t* data, struct
r = cpuid_identify_intel(raw, data, internal); r = cpuid_identify_intel(raw, data, internal);
break; break;
case VENDOR_AMD: case VENDOR_AMD:
case VENDOR_HYGON:
r = cpuid_identify_amd(raw, data, internal); r = cpuid_identify_amd(raw, data, internal);
break; break;
default: default:
@ -729,6 +731,7 @@ void cpuid_get_cpu_list(cpu_vendor_t vendor, struct cpu_list_t* list)
cpuid_get_list_intel(list); cpuid_get_list_intel(list);
break; break;
case VENDOR_AMD: case VENDOR_AMD:
case VENDOR_HYGON:
cpuid_get_list_amd(list); cpuid_get_list_amd(list);
break; break;
case VENDOR_CYRIX: case VENDOR_CYRIX:

View file

@ -110,6 +110,7 @@ typedef enum {
VENDOR_RISE, /*!< x86 CPU by Rise Technology */ VENDOR_RISE, /*!< x86 CPU by Rise Technology */
VENDOR_SIS, /*!< x86 CPU by SiS */ VENDOR_SIS, /*!< x86 CPU by SiS */
VENDOR_NSC, /*!< x86 CPU by National Semiconductor */ VENDOR_NSC, /*!< x86 CPU by National Semiconductor */
VENDOR_HYGON, /*!< Hygon CPU */
NUM_CPU_VENDORS, /*!< Valid CPU vendor ids: 0..NUM_CPU_VENDORS - 1 */ NUM_CPU_VENDORS, /*!< Valid CPU vendor ids: 0..NUM_CPU_VENDORS - 1 */
VENDOR_UNKNOWN = -1, VENDOR_UNKNOWN = -1,

View file

@ -99,6 +99,7 @@ enum _amd_bits_t {
_X6 = LBIT( 24 ), _X6 = LBIT( 24 ),
_FX = LBIT( 25 ), _FX = LBIT( 25 ),
_APU_ = LBIT( 26 ), _APU_ = LBIT( 26 ),
C86_ = LBIT( 27 ),
}; };
typedef enum _amd_bits_t amd_bits_t; typedef enum _amd_bits_t amd_bits_t;

View file

@ -765,7 +765,7 @@ static double get_info_min_multiplier(struct msr_info_t *info)
err = cpu_rdmsr_range(info->handle, MSR_PLATFORM_INFO, 47, 40, &reg); err = cpu_rdmsr_range(info->handle, MSR_PLATFORM_INFO, 47, 40, &reg);
if (!err) return (double) reg; if (!err) return (double) reg;
} }
else if(info->id->vendor == VENDOR_AMD) { else if(info->id->vendor == VENDOR_AMD || info->id->vendor == VENDOR_HYGON) {
/* N.B.: Find the last P-state /* N.B.: Find the last P-state
get_amd_last_pstate_addr() returns the last P-state, MSR_PSTATE_0 <= addr <= MSR_PSTATE_7 */ get_amd_last_pstate_addr() returns the last P-state, MSR_PSTATE_0 <= addr <= MSR_PSTATE_7 */
addr = get_amd_last_pstate_addr(info); addr = get_amd_last_pstate_addr(info);
@ -794,7 +794,7 @@ static double get_info_cur_multiplier(struct msr_info_t *info)
err = cpu_rdmsr_range(info->handle, IA32_PERF_STATUS, 15, 8, &reg); err = cpu_rdmsr_range(info->handle, IA32_PERF_STATUS, 15, 8, &reg);
if (!err) return (double) reg; if (!err) return (double) reg;
} }
else if(info->id->vendor == VENDOR_AMD) { else if(info->id->vendor == VENDOR_AMD || info->id->vendor == VENDOR_HYGON) {
/* Refer links above /* Refer links above
MSRC001_0063[2:0] is CurPstate */ MSRC001_0063[2:0] is CurPstate */
err = cpu_rdmsr_range(info->handle, MSR_PSTATE_S, 2, 0, &reg); err = cpu_rdmsr_range(info->handle, MSR_PSTATE_S, 2, 0, &reg);
@ -834,7 +834,7 @@ static double get_info_max_multiplier(struct msr_info_t *info)
err = cpu_rdmsr_range(info->handle, MSR_TURBO_RATIO_LIMIT, 7, 0, &reg); err = cpu_rdmsr_range(info->handle, MSR_TURBO_RATIO_LIMIT, 7, 0, &reg);
if (!err) return (double) reg; if (!err) return (double) reg;
} }
else if(info->id->vendor == VENDOR_AMD) { else if(info->id->vendor == VENDOR_AMD || info->id->vendor == VENDOR_HYGON) {
/* Refer links above /* Refer links above
MSRC001_0064 is Pb0 MSRC001_0064 is Pb0
Pb0 is the highest-performance boosted P-state */ Pb0 is the highest-performance boosted P-state */
@ -886,7 +886,7 @@ static double get_info_voltage(struct msr_info_t *info)
err = cpu_rdmsr_range(info->handle, MSR_PERF_STATUS, 47, 32, &reg); err = cpu_rdmsr_range(info->handle, MSR_PERF_STATUS, 47, 32, &reg);
if (!err) return (double) reg / (1 << 13); if (!err) return (double) reg / (1 << 13);
} }
else if(info->id->vendor == VENDOR_AMD) { else if(info->id->vendor == VENDOR_AMD || info->id->vendor == VENDOR_HYGON) {
/* Refer links above /* Refer links above
MSRC001_00[6B:64][15:9] is CpuVid (Jaguar and before) MSRC001_00[6B:64][15:9] is CpuVid (Jaguar and before)
MSRC001_00[6B:64][21:14] is CpuVid (Zen) MSRC001_00[6B:64][21:14] is CpuVid (Zen)
@ -926,7 +926,7 @@ static double get_info_bus_clock(struct msr_info_t *info)
err = cpu_rdmsr_range(info->handle, MSR_PLATFORM_INFO, 15, 8, &reg); err = cpu_rdmsr_range(info->handle, MSR_PLATFORM_INFO, 15, 8, &reg);
if (!err) return (double) info->cpu_clock / reg; if (!err) return (double) info->cpu_clock / reg;
} }
else if(info->id->vendor == VENDOR_AMD) { else if(info->id->vendor == VENDOR_AMD || info->id->vendor == VENDOR_HYGON) {
/* Refer links above /* Refer links above
MSRC001_0061[6:4] is PstateMaxVal MSRC001_0061[6:4] is PstateMaxVal
PstateMaxVal is the the lowest-performance non-boosted P-state */ PstateMaxVal is the the lowest-performance non-boosted P-state */
@ -1034,6 +1034,7 @@ int msr_serialize_raw_data(struct msr_driver_t* handle, const char* filename)
fprintf(f, "CPU is %s %s, stock clock is %dMHz.\n", id.vendor_str, id.brand_str, cpu_clock_measure(250, 1)); fprintf(f, "CPU is %s %s, stock clock is %dMHz.\n", id.vendor_str, id.brand_str, cpu_clock_measure(250, 1));
switch (id.vendor) { switch (id.vendor) {
case VENDOR_HYGON:
case VENDOR_AMD: msr = amd_msr; break; case VENDOR_AMD: msr = amd_msr; break;
case VENDOR_INTEL: msr = intel_msr; break; case VENDOR_INTEL: msr = intel_msr; break;
default: return set_error(ERR_CPU_UNKN); default: return set_error(ERR_CPU_UNKN);

View file

@ -251,7 +251,7 @@ static void adjust_march_ic_multiplier(const struct cpu_id_t* id, int* numerator
} }
// //
// Bulldozer or later: assume 1.4 IPC // Bulldozer or later: assume 1.4 IPC
if (id->vendor == VENDOR_AMD && id->ext_family >= 21) { if ((id->vendor == VENDOR_AMD && id->ext_family >= 21) || (id->vendor == VENDOR_HYGON)) {
debugf(1, "cpu_clock_by_ic: Bulldozer (or later) detected, dividing result by 1.4\n"); debugf(1, "cpu_clock_by_ic: Bulldozer (or later) detected, dividing result by 1.4\n");
*numerator = 5; *numerator = 5;
*denom = 7; // multiply by 5/7, to divide by 1.4 *denom = 7; // multiply by 5/7, to divide by 1.4

View file

@ -279,6 +279,10 @@ const struct match_entry_t cpudb_amd[] = {
{ 15, -1, -1, 23, 8, -1, -1, -1, NC, RYZEN_|_5 , 0, "Ryzen 5 (Pinnacle Ridge)" }, { 15, -1, -1, 23, 8, -1, -1, -1, NC, RYZEN_|_5 , 0, "Ryzen 5 (Pinnacle Ridge)" },
{ 15, -1, -1, 23, 8, -1, -1, -1, NC, RYZEN_|_3 , 0, "Ryzen 3 (Pinnacle Ridge)" }, { 15, -1, -1, 23, 8, -1, -1, -1, NC, RYZEN_|_3 , 0, "Ryzen 3 (Pinnacle Ridge)" },
{ 15, -1, -1, 24, 0, -1, -1, -1, NC, C86_|_7 , 0, "C86 7 (Dhyana)" },
{ 15, -1, -1, 24, 0, -1, -1, -1, NC, C86_|_5 , 0, "C86 5 (Dhyana)" },
{ 15, -1, -1, 24, 0, -1, -1, -1, NC, C86_|_3 , 0, "C86 3 (Dhyana)" },
/* Newer Opterons: */ /* Newer Opterons: */
{ 15, 9, -1, 22, 9, 8, -1, -1, NC, OPTERON_ , 0, "Magny-Cours Opteron" }, { 15, 9, -1, 22, 9, 8, -1, -1, NC, OPTERON_ , 0, "Magny-Cours Opteron" },
@ -459,6 +463,7 @@ static struct amd_code_and_bits_t decode_amd_codename_part1(const char *bs)
{ _APU_, " APU " }, { _APU_, " APU " },
{ EPYC_, "EPYC" }, { EPYC_, "EPYC" },
{ RYZEN_TR_, "Ryzen Threadripper" }, { RYZEN_TR_, "Ryzen Threadripper" },
{ C86_, "C86" },
}; };
for (i = 0; i < COUNT_OF(bit_matchtable); i++) { for (i = 0; i < COUNT_OF(bit_matchtable); i++) {
@ -478,6 +483,16 @@ static struct amd_code_and_bits_t decode_amd_codename_part1(const char *bs)
} }
} }
if ((i = match_pattern(bs, "C86 [357]")) != 0) {
bits |= C86_;
i--;
switch (bs[i + 6]) {
case '3': bits |= _3; break;
case '5': bits |= _5; break;
case '7': bits |= _7; break;
}
}
for (i = 0; i < COUNT_OF(code_matchtable); i++) for (i = 0; i < COUNT_OF(code_matchtable); i++)
if (match_pattern(bs, code_matchtable[i].search)) { if (match_pattern(bs, code_matchtable[i].search)) {
code = code_matchtable[i].c; code = code_matchtable[i].c;