diff --git a/LibreHardwareMonitorLib/Hardware/Cpu/Amd17Cpu.cs b/LibreHardwareMonitorLib/Hardware/Cpu/Amd17Cpu.cs index 4cb37fb..9f46e91 100644 --- a/LibreHardwareMonitorLib/Hardware/Cpu/Amd17Cpu.cs +++ b/LibreHardwareMonitorLib/Hardware/Cpu/Amd17Cpu.cs @@ -197,6 +197,12 @@ internal sealed class Amd17Cpu : AmdCpu supportsPerCcdTemperatures = true; break; + case 0x61: + sviPlane0Offset = F17H_M01H_SVI + 0x10; + sviPlane1Offset = F17H_M01H_SVI + 0xC; + supportsPerCcdTemperatures = true; + break; + default: // Zen and Zen+. sviPlane0Offset = F17H_M01H_SVI + 0xC; sviPlane1Offset = F17H_M01H_SVI + 0x10; @@ -278,12 +284,15 @@ internal sealed class Amd17Cpu : AmdCpu _cpu.ActivateSensor(_coreTemperatureTctlTdie); } - // Tested only on R5 3600 & Threadripper 3960X. + // Tested only on R5 3600 & Threadripper 3960X, 5900X, 7900X if (supportsPerCcdTemperatures) { for (uint i = 0; i < _ccdTemperatures.Length; i++) { - Ring0.WritePciConfig(0x00, FAMILY_17H_PCI_CONTROL_REGISTER, F17H_M70H_CCD1_TEMP + (i * 0x4)); + if (cpuId.Model == 0x61) + Ring0.WritePciConfig(0x00, FAMILY_17H_PCI_CONTROL_REGISTER, F17H_M61H_CCD1_TEMP + (i * 0x4)); + else + Ring0.WritePciConfig(0x00, FAMILY_17H_PCI_CONTROL_REGISTER, F17H_M70H_CCD1_TEMP + (i * 0x4)); Ring0.ReadPciConfig(0x00, FAMILY_17H_PCI_CONTROL_REGISTER + 4, out uint ccdRawTemp); ccdRawTemp &= 0xFFF; @@ -339,6 +348,9 @@ internal sealed class Amd17Cpu : AmdCpu double vcc; uint svi0PlaneXVddCor; + if (cpuId.Model is 0x61) // Readout not working for Ryzen 7000. + smuSvi0Tfn |= 0x01 | 0x02; + // Core (0x01). if ((smuSvi0Tfn & 0x01) == 0) { @@ -576,6 +588,7 @@ internal sealed class Amd17Cpu : AmdCpu private const uint F17H_M01H_SVI = 0x0005A000; private const uint F17H_M01H_THM_TCON_CUR_TMP = 0x00059800; private const uint F17H_M70H_CCD1_TEMP = 0x00059954; + private const uint F17H_M61H_CCD1_TEMP = 0x00059b08; private const uint F17H_TEMP_OFFSET_FLAG = 0x80000; private const uint FAMILY_17H_PCI_CONTROL_REGISTER = 0x60; private const uint HWCR = 0xC0010015; diff --git a/LibreHardwareMonitorLib/Hardware/RyzenSMU.cs b/LibreHardwareMonitorLib/Hardware/RyzenSMU.cs index de7a6ac..9e1b8ac 100644 --- a/LibreHardwareMonitorLib/Hardware/RyzenSMU.cs +++ b/LibreHardwareMonitorLib/Hardware/RyzenSMU.cs @@ -101,11 +101,55 @@ internal class RyzenSMU { 282, new SmuSensorType { Name = "Core #15 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, { 283, new SmuSensorType { Name = "Core #16 (Effective)", Type = SensorType.Clock, Scale = 1000 } } } + }, + { + // Zen 4. + 0x00540004, new Dictionary + { + { 3, new SmuSensorType { Name = "CPU PPT", Type = SensorType.Power, Scale = 1 } }, + { 11, new SmuSensorType { Name = "Package", Type = SensorType.Temperature, Scale = 1 } }, + { 20, new SmuSensorType { Name = "Core Power", Type = SensorType.Power, Scale = 1 } }, + { 21, new SmuSensorType { Name = "SOC Power", Type = SensorType.Power, Scale = 1 } }, + { 22, new SmuSensorType { Name = "Misc Power", Type = SensorType.Power, Scale = 1 } }, + { 26, new SmuSensorType { Name = "Total Power", Type = SensorType.Power, Scale = 1 } }, + { 47, new SmuSensorType { Name = "VDDCR", Type = SensorType.Voltage, Scale = 1 } }, + { 48, new SmuSensorType { Name = "TDC", Type = SensorType.Current, Scale = 1 } }, + { 49, new SmuSensorType { Name = "EDC", Type = SensorType.Current, Scale = 1 } }, + { 52, new SmuSensorType { Name = "VDDCR SoC", Type = SensorType.Voltage, Scale = 1 } }, + { 57, new SmuSensorType { Name = "VDD Misc", Type = SensorType.Voltage, Scale = 1 } }, + { 70, new SmuSensorType { Name = "Fabric", Type = SensorType.Clock, Scale = 1 } }, + { 74, new SmuSensorType { Name = "Uncore", Type = SensorType.Clock, Scale = 1 } }, + { 78, new SmuSensorType { Name = "Memory", Type = SensorType.Clock, Scale = 1 } }, + { 211, new SmuSensorType { Name = "IOD Hotspot", Type = SensorType.Temperature, Scale = 1 } }, + { 539, new SmuSensorType { Name = "L3 (CCD1)", Type = SensorType.Temperature, Scale = 1 } }, + { 540, new SmuSensorType { Name = "L3 (CCD2)", Type = SensorType.Temperature, Scale = 1 } }, + { 268, new SmuSensorType { Name = "LDO VDD", Type = SensorType.Voltage, Scale = 1 } }, + + // This is not working, some cores can be deactivated with the core disabled map. + // When Core 2 is disabled and Core 3 is enabled, the name of Core 3 == "Core 2". + //{ 357, new SmuSensorType { Name = "Core #1 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 358, new SmuSensorType { Name = "Core #2 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 359, new SmuSensorType { Name = "Core #3 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 360, new SmuSensorType { Name = "Core #4 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 361, new SmuSensorType { Name = "Core #5 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 362, new SmuSensorType { Name = "Core #6 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 363, new SmuSensorType { Name = "Core #7 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 364, new SmuSensorType { Name = "Core #8 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 365, new SmuSensorType { Name = "Core #9 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 366, new SmuSensorType { Name = "Core #10 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 367, new SmuSensorType { Name = "Core #11 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 368, new SmuSensorType { Name = "Core #12 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 369, new SmuSensorType { Name = "Core #13 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 370, new SmuSensorType { Name = "Core #14 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 371, new SmuSensorType { Name = "Core #15 (Effective)", Type = SensorType.Clock, Scale = 1000 } }, + //{ 372, new SmuSensorType { Name = "Core #16 (Effective)", Type = SensorType.Clock, Scale = 1000 } } + } } }; private uint _argsAddr; private uint _cmdAddr; + private uint _dramAddrHi; private uint _dramBaseAddr; private uint _pmTableSize; private uint _pmTableSizeAlt; @@ -121,16 +165,15 @@ internal class RyzenSMU if (_supportedCPU) { InpOut.Open(); - SetupPmTableAddrAndSize(); } } private static CpuCodeName GetCpuCodeName(uint family, uint model, uint packageType) { - if (family == 0x17) + return family switch { - return model switch + 0x17 => model switch { 0x01 => packageType == 7 ? CpuCodeName.Threadripper : CpuCodeName.SummitRidge, 0x08 => packageType == 7 ? CpuCodeName.Colfax : CpuCodeName.PinnacleRidge, @@ -142,22 +185,18 @@ internal class RyzenSMU 0x71 => CpuCodeName.Matisse, 0x90 => CpuCodeName.Vangogh, _ => CpuCodeName.Undefined - }; - } - - if (family == 0x19) - { - return model switch + }, + 0x19 => model switch { 0x00 => CpuCodeName.Milan, 0x20 or 0x21 => CpuCodeName.Vermeer, 0x40 => CpuCodeName.Rembrandt, 0x50 => CpuCodeName.Cezanne, + 0x61 => CpuCodeName.Raphael, _ => CpuCodeName.Undefined - }; - } - - return CpuCodeName.Undefined; + }, + _ => CpuCodeName.Undefined + }; } public string GetReport() @@ -196,6 +235,7 @@ internal class RyzenSMU case CpuCodeName.CastlePeak: case CpuCodeName.Matisse: case CpuCodeName.Vermeer: + case CpuCodeName.Raphael: _cmdAddr = 0x3B10524; _rspAddr = 0x3B10570; _argsAddr = 0x3B10A40; @@ -270,7 +310,9 @@ internal class RyzenSMU { float[] table = new float[_pmTableSize / 4]; - byte[] bytes = InpOut.ReadMemory(new IntPtr(_dramBaseAddr), _pmTableSize); + IntPtr pMemory = Environment.Is64BitProcess ? new IntPtr(_dramBaseAddr | (long)_dramAddrHi << 32) : new IntPtr(_dramBaseAddr); + + byte[] bytes = InpOut.ReadMemory(pMemory, _pmTableSize); if (bytes != null) Buffer.BlockCopy(bytes, 0, table, 0, bytes.Length); @@ -313,6 +355,7 @@ internal class RyzenSMU default: return; } + break; case CpuCodeName.Vermeer: @@ -339,6 +382,7 @@ internal class RyzenSMU default: return; } + break; case CpuCodeName.Renoir: @@ -363,6 +407,7 @@ internal class RyzenSMU default: return; } + break; case CpuCodeName.Cezanne: @@ -375,6 +420,7 @@ internal class RyzenSMU default: return; } + break; case CpuCodeName.Picasso: @@ -384,6 +430,19 @@ internal class RyzenSMU _pmTableSize = 0x608 + _pmTableSizeAlt; break; + case CpuCodeName.Raphael: + switch (_pmTableVersion) + { + case 0x00540004: + _pmTableSize = 0x948; + break; + + default: + return; + } + + break; + default: return; } @@ -407,6 +466,9 @@ internal class RyzenSMU case CpuCodeName.Renoir: fn = 0x06; break; + case CpuCodeName.Raphael: + fn = 0x05; + break; default: return false; } @@ -425,7 +487,8 @@ internal class RyzenSMU if (!command) return; - _dramBaseAddr = args[0] | (args[1] << 32); + _dramBaseAddr = args[0]; + _dramAddrHi = args[1]; } private void SetupAddrClass2(uint[] fn) @@ -492,25 +555,26 @@ internal class RyzenSMU switch (_cpuCodeName) { + case CpuCodeName.Raphael: + fn[0] = 0x04; + SetupAddrClass1(fn); + return; case CpuCodeName.Vermeer: case CpuCodeName.Matisse: case CpuCodeName.CastlePeak: fn[0] = 0x06; SetupAddrClass1(fn); return; - case CpuCodeName.Renoir: fn[0] = 0x66; SetupAddrClass1(fn); return; - case CpuCodeName.Colfax: case CpuCodeName.PinnacleRidge: fn[0] = 0x0b; fn[1] = 0x0c; SetupAddrClass2(fn); return; - case CpuCodeName.Dali: case CpuCodeName.Picasso: case CpuCodeName.RavenRidge: @@ -520,7 +584,6 @@ internal class RyzenSMU fn[2] = 0x0b; SetupAddrClass3(fn); return; - default: return; } @@ -533,23 +596,23 @@ internal class RyzenSMU switch (_cpuCodeName) { + case CpuCodeName.Raphael: + fn = 0x03; + break; case CpuCodeName.Matisse: case CpuCodeName.Vermeer: fn = 0x05; break; - case CpuCodeName.Renoir: args[0] = 3; fn = 0x65; break; - case CpuCodeName.Picasso: case CpuCodeName.RavenRidge: case CpuCodeName.RavenRidge2: args[0] = 3; fn = 0x3d; break; - default: return false; } @@ -678,10 +741,10 @@ internal class RyzenSMU private enum Status : uint { OK = 0x01, - Failed = 0xFF, - UnknownCmd = 0xFE, + CmdRejectedBusy = 0xFC, CmdRejectedPrereq = 0xFD, - CmdRejectedBusy = 0xFC + UnknownCmd = 0xFE, + Failed = 0xFF } private enum CpuCodeName @@ -702,6 +765,7 @@ internal class RyzenSMU Vangogh, Cezanne, Milan, - Dali + Dali, + Raphael } }