Boppity Bop
Boppity Bop

Reputation: 10473

Get SSD temperature in .NET

EDIT: Apparently Asus Strix X570 (my motherboard) does not have WMI interface so it has to be a non-WMI solution

I found this: How to read HardDisk Temperature?

However in 4.8 this throws exception (ran it as administrator): Not supported

var searcher = new ManagementObjectSearcher(
    "root\\WMI", "SELECT * FROM MSStorageDriver_ATAPISmartData");
foreach (ManagementObject queryObj in searcher.Get())

Also tried queries and got same exception:

SELECT * FROM MSStorageDriver_FailurePredictStatus
Select * from MSStorageDriver_FailurePredictData
Select * from MSStorageDriver_FailurePredictThresholds

Exception:

System.Management.ManagementException
  HResult=0x80131501
  Message=Not supported 
  Source=System.Management
  StackTrace:
   at System.Management.ManagementException.ThrowWithExtendedInfo(ManagementStatus errorCode)
   at System.Management.ManagementObjectCollection.ManagementObjectEnumerator.MoveNext()
   at myapp.TestSmart.GetDriveTemp() in TempSensor.cs:line 124
   at myapp.MainWindow.MainWindow_Loaded(Object sender, RoutedEventArgs e) in MainWindow.xaml.cs:line 157
   at System.Windows.EventRoute.InvokeHandlersImpl(Object source, RoutedEventArgs args, Boolean reRaised)
   at System.Windows.UIElement.RaiseEventImpl(DependencyObject sender, RoutedEventArgs args)
   at System.Windows.BroadcastEventHelper.BroadcastEvent(DependencyObject root, RoutedEvent routedEvent)
   at System.Windows.BroadcastEventHelper.BroadcastLoadedEvent(Object root)
   at MS.Internal.LoadedOrUnloadedOperation.DoWork()
   at System.Windows.Media.MediaContext.FireLoadedPendingCallbacks()
   at System.Windows.Media.MediaContext.FireInvokeOnRenderCallbacks()
   at System.Windows.Media.MediaContext.RenderMessageHandlerCore(Object resizedCompositionTarget)
   at System.Windows.Media.MediaContext.RenderMessageHandler(Object resizedCompositionTarget)
   at System.Windows.Interop.HwndTarget.OnResize()
   at System.Windows.Interop.HwndTarget.HandleMessage(WindowMessage msg, IntPtr wparam, IntPtr lparam)
   at System.Windows.Interop.HwndSource.HwndTargetFilterMessage(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled)
   at MS.Win32.HwndWrapper.WndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled)
   at MS.Win32.HwndSubclass.DispatcherCallbackOperation(Object o)
   at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs)
   at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Int32 numArgs, Delegate catchHandler)
   at System.Windows.Threading.Dispatcher.LegacyInvokeImpl(DispatcherPriority priority, TimeSpan timeout, Delegate method, Object args, Int32 numArgs)
   at MS.Win32.HwndSubclass.SubclassWndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam)

I need to measure M.2 SSD temperature on my machine.

The temperature is visible in the Windows Storage settings:

enter image description here

Also all SMART sensors visible on HWiNFO tool ran without administrator privilege:

enter image description here

Upvotes: 0

Views: 1077

Answers (1)

Boppity Bop
Boppity Bop

Reputation: 10473

Got LibreHardwareMonitor. Implemented class like this:

public class TempSensor
{
    Timer timer;
    private Computer computer;
    UpdateVisitor visitor;
    int interval;

    public event EventHandler<EventArgs2<float?,float?>> Ticked;

    public void Start(int interval = 1000)
    {
        this.interval = interval;

        visitor = new UpdateVisitor();

        computer = new Computer();

        computer.HardwareAdded += HardwareAdded;

        computer.Open();

        computer.IsCpuEnabled = true;
        computer.IsStorageEnabled = true;

        timer = new Timer(OnTimer);
        timer.Change(100, interval);
    }

    void OnTimer(object o)
    {
        computer.Accept(visitor);

        IList<ISensor> list = new List<ISensor>();
        SensorVisitor vis = new SensorVisitor(i => { list.Add(i); });

        vis.VisitComputer(computer);
            
        var sensors = list.Where(i => i.SensorType == SensorType.Temperature).ToList();
        var cpu = sensors.FirstOrDefault(i => i.Hardware.HardwareType == HardwareType.Cpu);
        var disk = sensors.FirstOrDefault(i => i.Hardware.HardwareType == HardwareType.Storage);

        if (Ticked != null)
            Ticked(this, new EventArgs2<float?,float?>(cpu?.Value, disk?.Value));

        timer.Change(interval, interval);
    }

    private void HardwareAdded(IHardware hardware)
    {
        foreach (ISensor sensor in hardware.Sensors)
            SensorAdded(sensor);

        hardware.SensorAdded += SensorAdded;

        foreach (IHardware subHardware in hardware.SubHardware)
            HardwareAdded(subHardware);
    }

    private void SensorAdded(ISensor sensor)
    {
    }
}

use like this:

sensor = new TempSensor();
sensor.Ticked += Sensor_Ticked;
sensor.Start(3019);

Upvotes: 1

Related Questions