Skip to content

Commit 026fa38

Browse files
committed
Merge remote-tracking branch 'lib/master' into dev
# Conflicts: # Hardware/Controller/Razer/RazerGroup.cs # Hardware/Memory/MemoryGroup.cs # LibreHardwareMonitorLib.csproj # Hardware/Memory/DimmMemory.cs # Hardware/Memory/GenericLinuxMemory.cs # Hardware/Memory/MemoryLinux.cs # Hardware/Memory/MemoryWindows.cs # Hardware/Memory/Sensors/SpdThermalSensor.cs # Hardware/Memory/TotalMemory.cs # Hardware/Memory/VirtualMemory.cs # Hardware/RAMSPDToolkitDriver.cs # Hardware/Ring0.cs # Interop/Ring0.cs
2 parents bfd7725 + 6c6cfa5 commit 026fa38

13 files changed

Lines changed: 778 additions & 156 deletions
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
using OpenHardwareMonitor.Hardware.Memory.Sensors;
2+
using RAMSPDToolkit.SPD;
3+
using RAMSPDToolkit.SPD.Enums;
4+
using RAMSPDToolkit.SPD.Interfaces;
5+
using RAMSPDToolkit.SPD.Interop.Shared;
6+
7+
namespace OpenHardwareMonitor.Hardware.Memory;
8+
9+
internal sealed class DimmMemory : Hardware
10+
{
11+
private readonly SpdThermalSensor _thermalSensor;
12+
13+
public DimmMemory(SPDAccessor accessor, string name, Identifier identifier, ISettings settings)
14+
: base(name, identifier, settings)
15+
{
16+
//Check which kind of RAM we have
17+
switch (accessor.MemoryType())
18+
{
19+
case SPDMemoryType.SPD_DDR4_SDRAM:
20+
case SPDMemoryType.SPD_DDR4E_SDRAM:
21+
case SPDMemoryType.SPD_LPDDR4_SDRAM:
22+
case SPDMemoryType.SPD_LPDDR4X_SDRAM:
23+
_thermalSensor = new SpdThermalSensor($"DIMM #{accessor.Index}",
24+
accessor.Index,
25+
SensorType.Temperature,
26+
this,
27+
settings,
28+
accessor as IThermalSensor);
29+
30+
break;
31+
case SPDMemoryType.SPD_DDR5_SDRAM:
32+
case SPDMemoryType.SPD_LPDDR5_SDRAM:
33+
//Check if we are on correct page or if write protection is not enabled
34+
if (accessor.PageData.HasFlag(PageData.ThermalData) || !accessor.HasSPDWriteProtection)
35+
{
36+
_thermalSensor = new SpdThermalSensor($"DIMM #{accessor.Index}",
37+
accessor.Index,
38+
SensorType.Temperature,
39+
this,
40+
settings,
41+
accessor as IThermalSensor);
42+
}
43+
44+
break;
45+
}
46+
47+
//Add thermal sensor
48+
if (_thermalSensor != null)
49+
ActivateSensor(_thermalSensor);
50+
}
51+
52+
public override HardwareType HardwareType => HardwareType.Memory;
53+
54+
public override void Update()
55+
{
56+
_thermalSensor?.UpdateSensor();
57+
}
58+
}

OpenHardwareMonitorLib/Hardware/Memory/GenericLinuxMemory.cs

Lines changed: 0 additions & 82 deletions
This file was deleted.

OpenHardwareMonitorLib/Hardware/Memory/GenericWindowsMemory.cs

Lines changed: 0 additions & 72 deletions
This file was deleted.

OpenHardwareMonitorLib/Hardware/Memory/MemoryGroup.cs

Lines changed: 111 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,68 @@
11
using System.Collections.Generic;
2+
using System.Timers;
3+
using RAMSPDToolkit.I2CSMBus;
4+
using RAMSPDToolkit.SPD;
5+
using RAMSPDToolkit.SPD.Enums;
6+
using RAMSPDToolkit.SPD.Interfaces;
7+
using RAMSPDToolkit.SPD.Interop.Shared;
8+
using RAMSPDToolkit.Windows.Driver;
29

310
namespace OpenHardwareMonitor.Hardware.Memory;
411

512
internal class MemoryGroup : IGroup
613
{
7-
private readonly Hardware[] _hardware;
14+
//Retry 12x
15+
private const int RetryCount = 12;
16+
17+
//Retry every 2.5 seconds
18+
private const double RetryTime = 2500;
19+
private static readonly object _lock = new();
20+
21+
private readonly List<Hardware> _hardware = [];
22+
private int _elapsedCounter;
23+
24+
private Timer _timer;
25+
26+
static MemoryGroup()
27+
{
28+
if (Ring0.IsOpen)
29+
{
30+
//Assign implementation of IDriver
31+
DriverManager.Driver = new RAMSPDToolkitDriver(Ring0.KernelDriver);
32+
SMBusManager.UseWMI = false;
33+
}
34+
}
835

936
public MemoryGroup(ISettings settings)
1037
{
11-
_hardware = [OperatingSystemHelper.IsUnix ? new GenericLinuxMemory("Memory", settings) : new GenericWindowsMemory("Memory", settings)];
38+
_hardware.Add(new VirtualMemory(settings));
39+
_hardware.Add(new TotalMemory(settings));
40+
41+
//No RAM detected
42+
if (!DetectThermalSensors(out List<SPDAccessor> accessors))
43+
{
44+
//Retry a couple of times
45+
//SMBus might not be detected right after boot
46+
_timer = new Timer(RetryTime);
47+
48+
_timer.Elapsed += (_, _) =>
49+
{
50+
if (_elapsedCounter++ >= RetryCount || DetectThermalSensors(out accessors))
51+
{
52+
_timer.Stop();
53+
_timer = null;
54+
55+
if (accessors != null)
56+
AddDimms(accessors, settings);
57+
}
58+
};
59+
60+
_timer.Start();
61+
}
62+
else
63+
{
64+
AddDimms(accessors, settings);
65+
}
1266
}
1367

1468
public string GetReport()
@@ -23,4 +77,59 @@ public void Close()
2377
foreach (Hardware ram in _hardware)
2478
ram.Close();
2579
}
80+
81+
private static bool DetectThermalSensors(out List<SPDAccessor> accessors)
82+
{
83+
lock (_lock)
84+
{
85+
var list = new List<SPDAccessor>();
86+
87+
bool ramDetected = false;
88+
89+
SMBusManager.DetectSMBuses();
90+
91+
//Go through detected SMBuses
92+
foreach (var smbus in SMBusManager.RegisteredSMBuses)
93+
{
94+
//Go through possible RAM slots
95+
for (byte i = SPDConstants.SPD_BEGIN; i <= SPDConstants.SPD_END; ++i)
96+
{
97+
//Detect type of RAM, if available
98+
var detector = new SPDDetector(smbus, i);
99+
100+
//RAM available and detected
101+
if (detector.Accessor != null)
102+
{
103+
//We are only interested in modules with thermal sensor
104+
if (detector.Accessor is IThermalSensor { HasThermalSensor: true })
105+
list.Add(detector.Accessor);
106+
107+
ramDetected = true;
108+
}
109+
}
110+
}
111+
112+
accessors = list.Count > 0 ? list : [];
113+
return ramDetected;
114+
}
115+
}
116+
117+
private void AddDimms(List<SPDAccessor> accessors, ISettings settings)
118+
{
119+
foreach (var ram in accessors)
120+
{
121+
//Default value
122+
string name = $"DIMM #{ram.Index}";
123+
124+
//Check if we can switch to the correct page
125+
if (ram.ChangePage(PageData.ModulePartNumber))
126+
{
127+
name = $"{ram.GetModuleManufacturerString()} - {ram.ModulePartNumber()} (#{ram.Index})";
128+
}
129+
130+
var memory = new DimmMemory(ram, name, new Identifier("ram"), settings);
131+
132+
_hardware.Add(memory);
133+
}
134+
}
26135
}

0 commit comments

Comments
 (0)