mirror of
https://github.com/openhardwaremonitor/openhardwaremonitor
synced 2025-08-22 09:57:20 +00:00
Added support for multiple processor groups. Changed the ThreadAffinity class to use a new struct GroupAffinity. Changed operating system checks to make use of a new flag OperatingSystem.IsUnix.
This commit is contained in:
parent
87c6f02d33
commit
b04c151c77
@ -130,8 +130,7 @@ namespace OpenHardwareMonitor.GUI {
|
|||||||
systemTray.HideShowCommand += hideShowClick;
|
systemTray.HideShowCommand += hideShowClick;
|
||||||
systemTray.ExitCommand += exitClick;
|
systemTray.ExitCommand += exitClick;
|
||||||
|
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (Hardware.OperatingSystem.IsUnix) { // Unix
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
|
||||||
treeView.RowHeight = Math.Max(treeView.RowHeight, 18);
|
treeView.RowHeight = Math.Max(treeView.RowHeight, 18);
|
||||||
splitContainer.BorderStyle = BorderStyle.None;
|
splitContainer.BorderStyle = BorderStyle.None;
|
||||||
splitContainer.Border3DStyle = Border3DStyle.Adjust;
|
splitContainer.Border3DStyle = Border3DStyle.Adjust;
|
||||||
|
@ -23,8 +23,7 @@ namespace OpenHardwareMonitor.GUI {
|
|||||||
private NotifyIconWindowsImplementation windowsNotifyIcon;
|
private NotifyIconWindowsImplementation windowsNotifyIcon;
|
||||||
|
|
||||||
public NotifyIconAdv() {
|
public NotifyIconAdv() {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (Hardware.OperatingSystem.IsUnix) { // Unix
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
|
||||||
genericNotifyIcon = new NotifyIcon();
|
genericNotifyIcon = new NotifyIcon();
|
||||||
} else { // Windows
|
} else { // Windows
|
||||||
windowsNotifyIcon = new NotifyIconWindowsImplementation();
|
windowsNotifyIcon = new NotifyIconWindowsImplementation();
|
||||||
|
@ -39,8 +39,7 @@ namespace OpenHardwareMonitor.GUI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public StartupManager() {
|
public StartupManager() {
|
||||||
int p = (int)System.Environment.OSVersion.Platform;
|
if (Hardware.OperatingSystem.IsUnix) {
|
||||||
if ((p == 4) || (p == 128)) {
|
|
||||||
scheduler = null;
|
scheduler = null;
|
||||||
isAvailable = false;
|
isAvailable = false;
|
||||||
return;
|
return;
|
||||||
|
@ -431,8 +431,7 @@ namespace OpenHardwareMonitor.Hardware.ATI {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static void CreateDelegates(string name) {
|
private static void CreateDelegates(string name) {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if ((p == 4) || (p == 128))
|
|
||||||
dllName = name + ".so";
|
dllName = name + ".so";
|
||||||
else
|
else
|
||||||
dllName = name + ".dll";
|
dllName = name + ".dll";
|
||||||
|
@ -129,8 +129,9 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
Thread.Sleep(1);
|
Thread.Sleep(1);
|
||||||
|
|
||||||
uint eax, edx;
|
uint eax, edx;
|
||||||
if (Ring0.RdmsrTx(FIDVID_STATUS, out eax, out edx,
|
if (Ring0.RdmsrTx(FIDVID_STATUS, out eax, out edx,
|
||||||
1UL << cpuid[i][0].Thread)) {
|
cpuid[i][0].Affinity))
|
||||||
|
{
|
||||||
// CurrFID can be found in eax bits 0-5, MaxFID in 16-21
|
// CurrFID can be found in eax bits 0-5, MaxFID in 16-21
|
||||||
// 8-13 hold StartFID, we don't use that here.
|
// 8-13 hold StartFID, we don't use that here.
|
||||||
double curMP = 0.5 * ((eax & 0x3F) + 8);
|
double curMP = 0.5 * ((eax & 0x3F) + 8);
|
||||||
|
@ -108,7 +108,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
corePerformanceBoostSupport = (cpuid[0][0].ExtData[7, 3] & (1 << 9)) > 0;
|
corePerformanceBoostSupport = (cpuid[0][0].ExtData[7, 3] & (1 << 9)) > 0;
|
||||||
|
|
||||||
// set affinity to the first thread for all frequency estimations
|
// set affinity to the first thread for all frequency estimations
|
||||||
ulong mask = ThreadAffinity.Set(1UL << cpuid[0][0].Thread);
|
var previousAffinity = ThreadAffinity.Set(cpuid[0][0].Affinity);
|
||||||
|
|
||||||
// disable core performance boost
|
// disable core performance boost
|
||||||
uint hwcrEax, hwcrEdx;
|
uint hwcrEax, hwcrEdx;
|
||||||
@ -132,12 +132,11 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
Ring0.Wrmsr(HWCR, hwcrEax, hwcrEdx);
|
Ring0.Wrmsr(HWCR, hwcrEax, hwcrEdx);
|
||||||
|
|
||||||
// restore the thread affinity.
|
// restore the thread affinity.
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
|
|
||||||
// the file reader for lm-sensors support on Linux
|
// the file reader for lm-sensors support on Linux
|
||||||
temperatureStream = null;
|
temperatureStream = null;
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix) {
|
||||||
if ((p == 4) || (p == 128)) {
|
|
||||||
string[] devicePaths = Directory.GetDirectories("/sys/class/hwmon/");
|
string[] devicePaths = Directory.GetDirectories("/sys/class/hwmon/");
|
||||||
foreach (string path in devicePaths) {
|
foreach (string path in devicePaths) {
|
||||||
string name = null;
|
string name = null;
|
||||||
@ -345,8 +344,8 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
Thread.Sleep(1);
|
Thread.Sleep(1);
|
||||||
|
|
||||||
uint curEax, curEdx;
|
uint curEax, curEdx;
|
||||||
if (Ring0.RdmsrTx(COFVID_STATUS, out curEax, out curEdx,
|
if (Ring0.RdmsrTx(COFVID_STATUS, out curEax, out curEdx,
|
||||||
1UL << cpuid[i][0].Thread))
|
cpuid[i][0].Affinity))
|
||||||
{
|
{
|
||||||
double multiplier;
|
double multiplier;
|
||||||
multiplier = GetCoreMultiplier(curEax);
|
multiplier = GetCoreMultiplier(curEax);
|
||||||
|
@ -272,7 +272,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
private class Core {
|
private class Core {
|
||||||
|
|
||||||
private readonly AMD17CPU cpu;
|
private readonly AMD17CPU cpu;
|
||||||
private readonly ulong threadAffinityMask;
|
private readonly GroupAffinity affinity;
|
||||||
|
|
||||||
private readonly Sensor powerSensor;
|
private readonly Sensor powerSensor;
|
||||||
private readonly Sensor clockSensor;
|
private readonly Sensor clockSensor;
|
||||||
@ -284,7 +284,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
public Core(int index, CPUID[] threads, AMD17CPU cpu, ISettings settings)
|
public Core(int index, CPUID[] threads, AMD17CPU cpu, ISettings settings)
|
||||||
{
|
{
|
||||||
this.cpu = cpu;
|
this.cpu = cpu;
|
||||||
this.threadAffinityMask = 1UL << threads[0].Thread;
|
this.affinity = threads[0].Affinity;
|
||||||
|
|
||||||
string coreString = cpu.CoreString(index);
|
string coreString = cpu.CoreString(index);
|
||||||
this.powerSensor =
|
this.powerSensor =
|
||||||
@ -294,7 +294,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
|
|
||||||
if (cpu.energyUnitMultiplier != 0) {
|
if (cpu.energyUnitMultiplier != 0) {
|
||||||
if (Ring0.RdmsrTx(MSR_CORE_ENERGY_STAT, out uint energyConsumed,
|
if (Ring0.RdmsrTx(MSR_CORE_ENERGY_STAT, out uint energyConsumed,
|
||||||
out _, threadAffinityMask))
|
out _, affinity))
|
||||||
{
|
{
|
||||||
lastEnergyTime = DateTime.UtcNow;
|
lastEnergyTime = DateTime.UtcNow;
|
||||||
lastEnergyConsumed = energyConsumed;
|
lastEnergyConsumed = energyConsumed;
|
||||||
@ -319,13 +319,13 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
DateTime energyTime = DateTime.MinValue;
|
DateTime energyTime = DateTime.MinValue;
|
||||||
double? multiplier = null;
|
double? multiplier = null;
|
||||||
|
|
||||||
ulong mask = ThreadAffinity.Set(threadAffinityMask);
|
var previousAffinity = ThreadAffinity.Set(affinity);
|
||||||
if (Ring0.Rdmsr(MSR_CORE_ENERGY_STAT, out uint energyConsumed, out _)) {
|
if (Ring0.Rdmsr(MSR_CORE_ENERGY_STAT, out uint energyConsumed, out _)) {
|
||||||
energyTime = DateTime.UtcNow;
|
energyTime = DateTime.UtcNow;
|
||||||
}
|
}
|
||||||
|
|
||||||
multiplier = GetMultiplier();
|
multiplier = GetMultiplier();
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
|
|
||||||
if (cpu.energyUnitMultiplier != 0) {
|
if (cpu.energyUnitMultiplier != 0) {
|
||||||
float deltaTime = (float)(energyTime - lastEnergyTime).TotalSeconds;
|
float deltaTime = (float)(energyTime - lastEnergyTime).TotalSeconds;
|
||||||
|
@ -23,10 +23,17 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
private static CPUID[][] GetProcessorThreads() {
|
private static CPUID[][] GetProcessorThreads() {
|
||||||
|
|
||||||
List<CPUID> threads = new List<CPUID>();
|
List<CPUID> threads = new List<CPUID>();
|
||||||
for (int i = 0; i < 64; i++) {
|
for (int i = 0; i < ThreadAffinity.ProcessorGroupCount; i++) {
|
||||||
try {
|
for (int j = 0; j < 64; j++) {
|
||||||
threads.Add(new CPUID(i));
|
try {
|
||||||
} catch (ArgumentOutOfRangeException) { }
|
if (!ThreadAffinity.IsValid(GroupAffinity.Single((ushort)i, j)))
|
||||||
|
continue;
|
||||||
|
var cpuid = CPUID.Get(i, j);
|
||||||
|
if (cpuid != null)
|
||||||
|
threads.Add(cpuid);
|
||||||
|
} catch (ArgumentOutOfRangeException) {
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
SortedDictionary<uint, List<CPUID>> processors =
|
SortedDictionary<uint, List<CPUID>> processors =
|
||||||
@ -172,6 +179,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
r.AppendLine();
|
r.AppendLine();
|
||||||
for (int j = 0; j < threads[i].Length; j++)
|
for (int j = 0; j < threads[i].Length; j++)
|
||||||
for (int k = 0; k < threads[i][j].Length; k++) {
|
for (int k = 0; k < threads[i][j].Length; k++) {
|
||||||
|
r.AppendLine(" CPU Group: " + threads[i][j][k].Group);
|
||||||
r.AppendLine(" CPU Thread: " + threads[i][j][k].Thread);
|
r.AppendLine(" CPU Thread: " + threads[i][j][k].Thread);
|
||||||
r.AppendLine(" APIC ID: " + threads[i][j][k].ApicId);
|
r.AppendLine(" APIC ID: " + threads[i][j][k].ApicId);
|
||||||
r.AppendLine(" Processor ID: " + threads[i][j][k].ProcessorId);
|
r.AppendLine(" Processor ID: " + threads[i][j][k].ProcessorId);
|
||||||
|
@ -21,7 +21,9 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
|
|
||||||
internal class CPUID {
|
internal class CPUID {
|
||||||
|
|
||||||
|
private readonly int group;
|
||||||
private readonly int thread;
|
private readonly int thread;
|
||||||
|
private readonly GroupAffinity affinity;
|
||||||
|
|
||||||
private readonly Vendor vendor = Vendor.Unknown;
|
private readonly Vendor vendor = Vendor.Unknown;
|
||||||
|
|
||||||
@ -68,83 +70,87 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
return count;
|
return count;
|
||||||
}
|
}
|
||||||
|
|
||||||
public CPUID(int thread) {
|
public static CPUID Get(int group, int thread) {
|
||||||
|
if (thread >= 64)
|
||||||
|
return null;
|
||||||
|
|
||||||
|
var affinity = GroupAffinity.Single((ushort)group, thread);
|
||||||
|
|
||||||
|
var previousAffinity = ThreadAffinity.Set(affinity);
|
||||||
|
if (previousAffinity == GroupAffinity.Undefined)
|
||||||
|
return null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
return new CPUID(group, thread, affinity);
|
||||||
|
} finally {
|
||||||
|
ThreadAffinity.Set(previousAffinity);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private CPUID(int group, int thread, GroupAffinity affinity) {
|
||||||
|
this.group = group;
|
||||||
this.thread = thread;
|
this.thread = thread;
|
||||||
|
this.affinity = affinity;
|
||||||
|
|
||||||
uint maxCpuid = 0;
|
uint maxCpuid = 0;
|
||||||
uint maxCpuidExt = 0;
|
uint maxCpuidExt = 0;
|
||||||
|
|
||||||
uint eax, ebx, ecx, edx;
|
uint eax, ebx, ecx, edx;
|
||||||
|
|
||||||
if (thread >= 64)
|
Opcode.Cpuid(CPUID_0, 0, out eax, out ebx, out ecx, out edx);
|
||||||
throw new ArgumentOutOfRangeException("thread");
|
if (eax > 0)
|
||||||
ulong mask = 1UL << thread;
|
maxCpuid = eax;
|
||||||
|
else
|
||||||
|
return;
|
||||||
|
|
||||||
if (Opcode.CpuidTx(CPUID_0, 0,
|
StringBuilder vendorBuilder = new StringBuilder();
|
||||||
out eax, out ebx, out ecx, out edx, mask)) {
|
AppendRegister(vendorBuilder, ebx);
|
||||||
if (eax > 0)
|
AppendRegister(vendorBuilder, edx);
|
||||||
maxCpuid = eax;
|
AppendRegister(vendorBuilder, ecx);
|
||||||
else
|
string cpuVendor = vendorBuilder.ToString();
|
||||||
return;
|
switch (cpuVendor) {
|
||||||
|
case "GenuineIntel":
|
||||||
StringBuilder vendorBuilder = new StringBuilder();
|
vendor = Vendor.Intel;
|
||||||
AppendRegister(vendorBuilder, ebx);
|
break;
|
||||||
AppendRegister(vendorBuilder, edx);
|
case "AuthenticAMD":
|
||||||
AppendRegister(vendorBuilder, ecx);
|
vendor = Vendor.AMD;
|
||||||
string cpuVendor = vendorBuilder.ToString();
|
break;
|
||||||
switch (cpuVendor) {
|
default:
|
||||||
case "GenuineIntel":
|
vendor = Vendor.Unknown;
|
||||||
vendor = Vendor.Intel;
|
break;
|
||||||
break;
|
|
||||||
case "AuthenticAMD":
|
|
||||||
vendor = Vendor.AMD;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
vendor = Vendor.Unknown;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
eax = ebx = ecx = edx = 0;
|
|
||||||
if (Opcode.CpuidTx(CPUID_EXT, 0,
|
|
||||||
out eax, out ebx, out ecx, out edx, mask)) {
|
|
||||||
if (eax > CPUID_EXT)
|
|
||||||
maxCpuidExt = eax - CPUID_EXT;
|
|
||||||
else
|
|
||||||
return;
|
|
||||||
} else {
|
|
||||||
throw new ArgumentOutOfRangeException("thread");
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new ArgumentOutOfRangeException("thread");
|
|
||||||
}
|
}
|
||||||
|
eax = ebx = ecx = edx = 0;
|
||||||
|
Opcode.Cpuid(CPUID_EXT, 0, out eax, out ebx, out ecx, out edx);
|
||||||
|
if (eax > CPUID_EXT)
|
||||||
|
maxCpuidExt = eax - CPUID_EXT;
|
||||||
|
else
|
||||||
|
return;
|
||||||
|
|
||||||
maxCpuid = Math.Min(maxCpuid, 1024);
|
maxCpuid = Math.Min(maxCpuid, 1024);
|
||||||
maxCpuidExt = Math.Min(maxCpuidExt, 1024);
|
maxCpuidExt = Math.Min(maxCpuidExt, 1024);
|
||||||
|
|
||||||
cpuidData = new uint[maxCpuid + 1, 4];
|
cpuidData = new uint[maxCpuid + 1, 4];
|
||||||
for (uint i = 0; i < (maxCpuid + 1); i++)
|
for (uint i = 0; i < (maxCpuid + 1); i++)
|
||||||
Opcode.CpuidTx(CPUID_0 + i, 0,
|
Opcode.Cpuid(CPUID_0 + i, 0,
|
||||||
out cpuidData[i, 0], out cpuidData[i, 1],
|
out cpuidData[i, 0], out cpuidData[i, 1],
|
||||||
out cpuidData[i, 2], out cpuidData[i, 3], mask);
|
out cpuidData[i, 2], out cpuidData[i, 3]);
|
||||||
|
|
||||||
cpuidExtData = new uint[maxCpuidExt + 1, 4];
|
cpuidExtData = new uint[maxCpuidExt + 1, 4];
|
||||||
for (uint i = 0; i < (maxCpuidExt + 1); i++)
|
for (uint i = 0; i < (maxCpuidExt + 1); i++)
|
||||||
Opcode.CpuidTx(CPUID_EXT + i, 0,
|
Opcode.Cpuid(CPUID_EXT + i, 0,
|
||||||
out cpuidExtData[i, 0], out cpuidExtData[i, 1],
|
out cpuidExtData[i, 0], out cpuidExtData[i, 1],
|
||||||
out cpuidExtData[i, 2], out cpuidExtData[i, 3], mask);
|
out cpuidExtData[i, 2], out cpuidExtData[i, 3]);
|
||||||
|
|
||||||
StringBuilder nameBuilder = new StringBuilder();
|
StringBuilder nameBuilder = new StringBuilder();
|
||||||
for (uint i = 2; i <= 4; i++) {
|
for (uint i = 2; i <= 4; i++) {
|
||||||
if (Opcode.CpuidTx(CPUID_EXT + i, 0,
|
Opcode.Cpuid(CPUID_EXT + i, 0, out eax, out ebx, out ecx, out edx);
|
||||||
out eax, out ebx, out ecx, out edx, mask))
|
AppendRegister(nameBuilder, eax);
|
||||||
{
|
AppendRegister(nameBuilder, ebx);
|
||||||
AppendRegister(nameBuilder, eax);
|
AppendRegister(nameBuilder, ecx);
|
||||||
AppendRegister(nameBuilder, ebx);
|
AppendRegister(nameBuilder, edx);
|
||||||
AppendRegister(nameBuilder, ecx);
|
|
||||||
AppendRegister(nameBuilder, edx);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
nameBuilder.Replace('\0', ' ');
|
nameBuilder.Replace('\0', ' ');
|
||||||
cpuBrandString = nameBuilder.ToString().Trim();
|
cpuBrandString = nameBuilder.ToString().Trim();
|
||||||
nameBuilder.Replace("Dual-Core Processor", "");
|
nameBuilder.Replace("Dual-Core Processor", "");
|
||||||
nameBuilder.Replace("Triple-Core Processor", "");
|
nameBuilder.Replace("Triple-Core Processor", "");
|
||||||
nameBuilder.Replace("Quad-Core Processor", "");
|
nameBuilder.Replace("Quad-Core Processor", "");
|
||||||
@ -175,7 +181,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
nameBuilder.Replace("RADEON R5, 10 COMPUTE CORES 4C+6G", "");
|
nameBuilder.Replace("RADEON R5, 10 COMPUTE CORES 4C+6G", "");
|
||||||
nameBuilder.Replace("RADEON R7, 10 COMPUTE CORES 4C+6G", "");
|
nameBuilder.Replace("RADEON R7, 10 COMPUTE CORES 4C+6G", "");
|
||||||
nameBuilder.Replace("RADEON R7, 12 COMPUTE CORES 4C+8G", "");
|
nameBuilder.Replace("RADEON R7, 12 COMPUTE CORES 4C+8G", "");
|
||||||
nameBuilder.Replace("Radeon R5, 6 Compute Cores 2C+4G", "");
|
nameBuilder.Replace("Radeon R5, 6 Compute Cores 2C+4G", "");
|
||||||
nameBuilder.Replace("Radeon R5, 8 Compute Cores 4C+4G", "");
|
nameBuilder.Replace("Radeon R5, 8 Compute Cores 4C+4G", "");
|
||||||
nameBuilder.Replace("Radeon R6, 10 Compute Cores 4C+6G", "");
|
nameBuilder.Replace("Radeon R6, 10 Compute Cores 4C+6G", "");
|
||||||
nameBuilder.Replace("Radeon R7, 10 Compute Cores 4C+6G", "");
|
nameBuilder.Replace("Radeon R7, 10 Compute Cores 4C+6G", "");
|
||||||
@ -191,7 +197,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
name = nameBuilder.ToString();
|
name = nameBuilder.ToString();
|
||||||
if (name.Contains("@"))
|
if (name.Contains("@"))
|
||||||
name = name.Remove(name.LastIndexOf('@'));
|
name = name.Remove(name.LastIndexOf('@'));
|
||||||
name = name.Trim();
|
name = name.Trim();
|
||||||
|
|
||||||
this.family = ((cpuidData[1, 0] & 0x0FF00000) >> 20) +
|
this.family = ((cpuidData[1, 0] & 0x0FF00000) >> 20) +
|
||||||
((cpuidData[1, 0] & 0x0F00) >> 8);
|
((cpuidData[1, 0] & 0x0F00) >> 8);
|
||||||
@ -209,14 +215,14 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
maxCoreIdPerPackage = ((cpuidData[4, 0] >> 26) & 0x3F) + 1;
|
maxCoreIdPerPackage = ((cpuidData[4, 0] >> 26) & 0x3F) + 1;
|
||||||
else
|
else
|
||||||
maxCoreIdPerPackage = 1;
|
maxCoreIdPerPackage = 1;
|
||||||
threadMaskWith =
|
threadMaskWith =
|
||||||
NextLog2(maxCoreAndThreadIdPerPackage / maxCoreIdPerPackage);
|
NextLog2(maxCoreAndThreadIdPerPackage / maxCoreIdPerPackage);
|
||||||
coreMaskWith = NextLog2(maxCoreIdPerPackage);
|
coreMaskWith = NextLog2(maxCoreIdPerPackage);
|
||||||
break;
|
break;
|
||||||
case Vendor.AMD:
|
case Vendor.AMD:
|
||||||
if (this.family == 0x17) {
|
if (this.family == 0x17) {
|
||||||
coreMaskWith = (cpuidExtData[8, 2] >> 12) & 0xF;
|
coreMaskWith = (cpuidExtData[8, 2] >> 12) & 0xF;
|
||||||
threadMaskWith =
|
threadMaskWith =
|
||||||
NextLog2(((cpuidExtData[0x1E, 1] >> 8) & 0xFF) + 1);
|
NextLog2(((cpuidExtData[0x1E, 1] >> 8) & 0xFF) + 1);
|
||||||
} else {
|
} else {
|
||||||
uint corePerPackage;
|
uint corePerPackage;
|
||||||
@ -226,7 +232,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
corePerPackage = 1;
|
corePerPackage = 1;
|
||||||
coreMaskWith = NextLog2(corePerPackage);
|
coreMaskWith = NextLog2(corePerPackage);
|
||||||
threadMaskWith = 0;
|
threadMaskWith = 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
threadMaskWith = 0;
|
threadMaskWith = 0;
|
||||||
@ -235,11 +241,11 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
}
|
}
|
||||||
|
|
||||||
processorId = (apicId >> (int)(coreMaskWith + threadMaskWith));
|
processorId = (apicId >> (int)(coreMaskWith + threadMaskWith));
|
||||||
coreId = ((apicId >> (int)(threadMaskWith))
|
coreId = ((apicId >> (int)(threadMaskWith))
|
||||||
- (processorId << (int)(coreMaskWith)));
|
- (processorId << (int)(coreMaskWith)));
|
||||||
threadId = apicId
|
threadId = apicId
|
||||||
- (processorId << (int)(coreMaskWith + threadMaskWith))
|
- (processorId << (int)(coreMaskWith + threadMaskWith))
|
||||||
- (coreId << (int)(threadMaskWith));
|
- (coreId << (int)(threadMaskWith));
|
||||||
}
|
}
|
||||||
|
|
||||||
public string Name {
|
public string Name {
|
||||||
@ -250,10 +256,22 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
get { return cpuBrandString; }
|
get { return cpuBrandString; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public int Group {
|
||||||
|
get {
|
||||||
|
return group;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public int Thread {
|
public int Thread {
|
||||||
get { return thread; }
|
get { return thread; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public GroupAffinity Affinity {
|
||||||
|
get {
|
||||||
|
return affinity;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public Vendor Vendor {
|
public Vendor Vendor {
|
||||||
get { return vendor; }
|
get { return vendor; }
|
||||||
}
|
}
|
||||||
|
@ -106,13 +106,13 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (hasTimeStampCounter) {
|
if (hasTimeStampCounter) {
|
||||||
ulong mask = ThreadAffinity.Set(1UL << cpuid[0][0].Thread);
|
var previousAffinity = ThreadAffinity.Set(cpuid[0][0].Affinity);
|
||||||
|
|
||||||
EstimateTimeStampCounterFrequency(
|
EstimateTimeStampCounterFrequency(
|
||||||
out estimatedTimeStampCounterFrequency,
|
out estimatedTimeStampCounterFrequency,
|
||||||
out estimatedTimeStampCounterFrequencyError);
|
out estimatedTimeStampCounterFrequencyError);
|
||||||
|
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
} else {
|
} else {
|
||||||
estimatedTimeStampCounterFrequency = 0;
|
estimatedTimeStampCounterFrequency = 0;
|
||||||
}
|
}
|
||||||
@ -185,9 +185,11 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private static void AppendMSRData(StringBuilder r, uint msr, int thread) {
|
private static void AppendMSRData(StringBuilder r, uint msr,
|
||||||
|
GroupAffinity affinity)
|
||||||
|
{
|
||||||
uint eax, edx;
|
uint eax, edx;
|
||||||
if (Ring0.RdmsrTx(msr, out eax, out edx, 1UL << thread)) {
|
if (Ring0.RdmsrTx(msr, out eax, out edx, affinity)) {
|
||||||
r.Append(" ");
|
r.Append(" ");
|
||||||
r.Append((msr).ToString("X8", CultureInfo.InvariantCulture));
|
r.Append((msr).ToString("X8", CultureInfo.InvariantCulture));
|
||||||
r.Append(" ");
|
r.Append(" ");
|
||||||
@ -240,7 +242,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
r.AppendLine();
|
r.AppendLine();
|
||||||
r.AppendLine(" MSR EDX EAX");
|
r.AppendLine(" MSR EDX EAX");
|
||||||
foreach (uint msr in msrArray)
|
foreach (uint msr in msrArray)
|
||||||
AppendMSRData(r, msr, cpuid[i][0].Thread);
|
AppendMSRData(r, msr, cpuid[i][0].Affinity);
|
||||||
r.AppendLine();
|
r.AppendLine();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -268,15 +270,15 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
if (hasTimeStampCounter && isInvariantTimeStampCounter) {
|
if (hasTimeStampCounter && isInvariantTimeStampCounter) {
|
||||||
|
|
||||||
// make sure always the same thread is used
|
// make sure always the same thread is used
|
||||||
ulong mask = ThreadAffinity.Set(1UL << cpuid[0][0].Thread);
|
var previousAffinity = ThreadAffinity.Set(cpuid[0][0].Affinity);
|
||||||
|
|
||||||
// read time before and after getting the TSC to estimate the error
|
// read time before and after getting the TSC to estimate the error
|
||||||
long firstTime = Stopwatch.GetTimestamp();
|
long firstTime = Stopwatch.GetTimestamp();
|
||||||
ulong timeStampCount = Opcode.Rdtsc();
|
ulong timeStampCount = Opcode.Rdtsc();
|
||||||
long time = Stopwatch.GetTimestamp();
|
long time = Stopwatch.GetTimestamp();
|
||||||
|
|
||||||
// restore the thread affinity mask
|
// restore the previous thread affinity mask
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
|
|
||||||
double delta = ((double)(time - lastTime)) / Stopwatch.Frequency;
|
double delta = ((double)(time - lastTime)) / Stopwatch.Frequency;
|
||||||
double error = ((double)(time - firstTime)) / Stopwatch.Frequency;
|
double error = ((double)(time - firstTime)) / Stopwatch.Frequency;
|
||||||
|
@ -79,7 +79,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
float[] result = new float[coreCount];
|
float[] result = new float[coreCount];
|
||||||
for (int i = 0; i < coreCount; i++) {
|
for (int i = 0; i < coreCount; i++) {
|
||||||
if (Ring0.RdmsrTx(IA32_TEMPERATURE_TARGET, out eax,
|
if (Ring0.RdmsrTx(IA32_TEMPERATURE_TARGET, out eax,
|
||||||
out edx, 1UL << cpuid[i][0].Thread)) {
|
out edx, cpuid[i][0].Affinity)) {
|
||||||
result[i] = (eax >> 16) & 0xFF;
|
result[i] = (eax >> 16) & 0xFF;
|
||||||
} else {
|
} else {
|
||||||
result[i] = 100;
|
result[i] = 100;
|
||||||
@ -419,7 +419,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
uint eax, edx;
|
uint eax, edx;
|
||||||
// if reading is valid
|
// if reading is valid
|
||||||
if (Ring0.RdmsrTx(IA32_THERM_STATUS_MSR, out eax, out edx,
|
if (Ring0.RdmsrTx(IA32_THERM_STATUS_MSR, out eax, out edx,
|
||||||
1UL << cpuid[i][0].Thread) && (eax & 0x80000000) != 0)
|
cpuid[i][0].Affinity) && (eax & 0x80000000) != 0)
|
||||||
{
|
{
|
||||||
// get the dist from tjMax from bits 22:16
|
// get the dist from tjMax from bits 22:16
|
||||||
float deltaT = ((eax & 0x007F0000) >> 16);
|
float deltaT = ((eax & 0x007F0000) >> 16);
|
||||||
@ -435,7 +435,7 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
uint eax, edx;
|
uint eax, edx;
|
||||||
// if reading is valid
|
// if reading is valid
|
||||||
if (Ring0.RdmsrTx(IA32_PACKAGE_THERM_STATUS, out eax, out edx,
|
if (Ring0.RdmsrTx(IA32_PACKAGE_THERM_STATUS, out eax, out edx,
|
||||||
1UL << cpuid[0][0].Thread) && (eax & 0x80000000) != 0)
|
cpuid[0][0].Affinity) && (eax & 0x80000000) != 0)
|
||||||
{
|
{
|
||||||
// get the dist from tjMax from bits 22:16
|
// get the dist from tjMax from bits 22:16
|
||||||
float deltaT = ((eax & 0x007F0000) >> 16);
|
float deltaT = ((eax & 0x007F0000) >> 16);
|
||||||
@ -452,8 +452,9 @@ namespace OpenHardwareMonitor.Hardware.CPU {
|
|||||||
uint eax, edx;
|
uint eax, edx;
|
||||||
for (int i = 0; i < coreClocks.Length; i++) {
|
for (int i = 0; i < coreClocks.Length; i++) {
|
||||||
System.Threading.Thread.Sleep(1);
|
System.Threading.Thread.Sleep(1);
|
||||||
if (Ring0.RdmsrTx(IA32_PERF_STATUS, out eax, out edx,
|
if (Ring0.RdmsrTx(IA32_PERF_STATUS, out eax, out edx,
|
||||||
1UL << cpuid[i][0].Thread)) {
|
cpuid[i][0].Affinity))
|
||||||
|
{
|
||||||
newBusClock =
|
newBusClock =
|
||||||
TimeStampCounterFrequency / timeStampCounterMultiplier;
|
TimeStampCounterFrequency / timeStampCounterMultiplier;
|
||||||
switch (microarchitecture) {
|
switch (microarchitecture) {
|
||||||
|
57
Hardware/GroupAffinity.cs
Normal file
57
Hardware/GroupAffinity.cs
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
This Source Code Form is subject to the terms of the Mozilla Public
|
||||||
|
License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
|
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
|
||||||
|
Copyright (C) 2020 Michael Möller <mmoeller@openhardwaremonitor.org>
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
|
namespace OpenHardwareMonitor.Hardware {
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// This structure describes a group-specific affinity.
|
||||||
|
/// </summary>
|
||||||
|
internal struct GroupAffinity {
|
||||||
|
|
||||||
|
public static GroupAffinity Undefined =
|
||||||
|
new GroupAffinity(ushort.MaxValue, 0);
|
||||||
|
|
||||||
|
public GroupAffinity(ushort group, ulong mask) {
|
||||||
|
this.Group = group;
|
||||||
|
this.Mask = mask;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static GroupAffinity Single(ushort group, int index) {
|
||||||
|
return new GroupAffinity(group, 1UL << index);
|
||||||
|
}
|
||||||
|
|
||||||
|
public ushort Group { get; }
|
||||||
|
|
||||||
|
public ulong Mask { get; }
|
||||||
|
|
||||||
|
public override bool Equals(object o) {
|
||||||
|
if (o == null || GetType() != o.GetType()) return false;
|
||||||
|
GroupAffinity a = (GroupAffinity)o;
|
||||||
|
return (Group == a.Group) && (Mask == a.Mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override int GetHashCode() {
|
||||||
|
return Group.GetHashCode() ^ Mask.GetHashCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static bool operator ==(GroupAffinity a1, GroupAffinity a2) {
|
||||||
|
return (a1.Group == a2.Group) && (a1.Mask == a2.Mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static bool operator !=(GroupAffinity a1, GroupAffinity a2) {
|
||||||
|
return (a1.Group != a2.Group) || (a1.Mask != a2.Mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
@ -24,8 +24,8 @@ namespace OpenHardwareMonitor.Hardware.HDD {
|
|||||||
new List<AbstractHarddrive>();
|
new List<AbstractHarddrive>();
|
||||||
|
|
||||||
public HarddriveGroup(ISettings settings) {
|
public HarddriveGroup(ISettings settings) {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if (p == 4 || p == 128) return;
|
return;
|
||||||
|
|
||||||
ISmart smart = new WindowsSmart();
|
ISmart smart = new WindowsSmart();
|
||||||
|
|
||||||
|
@ -66,9 +66,8 @@ namespace OpenHardwareMonitor.Hardware.Heatmaster {
|
|||||||
|
|
||||||
public HeatmasterGroup(ISettings settings) {
|
public HeatmasterGroup(ISettings settings) {
|
||||||
|
|
||||||
// No implementation for Heatmaster on Unix systems
|
// No implementation for Heatmaster on Unix systems
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if ((p == 4) || (p == 128))
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
string[] portNames = GetRegistryPortNames();
|
string[] portNames = GetRegistryPortNames();
|
||||||
|
@ -50,8 +50,7 @@ namespace OpenHardwareMonitor.Hardware.Mainboard {
|
|||||||
new Identifier(Identifier, "name").ToString(), name);
|
new Identifier(Identifier, "name").ToString(), name);
|
||||||
|
|
||||||
ISuperIO[] superIO;
|
ISuperIO[] superIO;
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix) {
|
||||||
if ((p == 4) || (p == 128)) {
|
|
||||||
this.lmSensors = new LMSensors();
|
this.lmSensors = new LMSensors();
|
||||||
superIO = lmSensors.SuperIO;
|
superIO = lmSensors.SuperIO;
|
||||||
} else {
|
} else {
|
||||||
|
@ -61,8 +61,7 @@ namespace OpenHardwareMonitor.Hardware.Nvidia {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static string GetDllName() {
|
private static string GetDllName() {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if ((p == 4) || (p == 128))
|
|
||||||
return "libnvidia-ml.so";
|
return "libnvidia-ml.so";
|
||||||
else
|
else
|
||||||
return "nvml.dll";
|
return "nvml.dll";
|
||||||
|
@ -18,9 +18,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
private static IntPtr codeBuffer;
|
private static IntPtr codeBuffer;
|
||||||
private static ulong size;
|
private static ulong size;
|
||||||
|
|
||||||
public static void Open() {
|
public static void Open() {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
|
||||||
|
|
||||||
byte[] rdtscCode;
|
byte[] rdtscCode;
|
||||||
byte[] cpuidCode;
|
byte[] cpuidCode;
|
||||||
if (IntPtr.Size == 4) {
|
if (IntPtr.Size == 4) {
|
||||||
@ -29,7 +27,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
} else {
|
} else {
|
||||||
rdtscCode = RDTSC_64;
|
rdtscCode = RDTSC_64;
|
||||||
|
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
if (OperatingSystem.IsUnix) { // Unix
|
||||||
cpuidCode = CPUID_64_LINUX;
|
cpuidCode = CPUID_64_LINUX;
|
||||||
} else { // Windows
|
} else { // Windows
|
||||||
cpuidCode = CPUID_64_WINDOWS;
|
cpuidCode = CPUID_64_WINDOWS;
|
||||||
@ -38,7 +36,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
|
|
||||||
size = (ulong)(rdtscCode.Length + cpuidCode.Length);
|
size = (ulong)(rdtscCode.Length + cpuidCode.Length);
|
||||||
|
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
if (OperatingSystem.IsUnix) { // Unix
|
||||||
Assembly assembly =
|
Assembly assembly =
|
||||||
Assembly.Load("Mono.Posix, Version=2.0.0.0, Culture=neutral, " +
|
Assembly.Load("Mono.Posix, Version=2.0.0.0, Culture=neutral, " +
|
||||||
"PublicKeyToken=0738eb9f132ed756");
|
"PublicKeyToken=0738eb9f132ed756");
|
||||||
@ -81,8 +79,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
Rdtsc = null;
|
Rdtsc = null;
|
||||||
Cpuid = null;
|
Cpuid = null;
|
||||||
|
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix) { // Unix
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
|
||||||
Assembly assembly =
|
Assembly assembly =
|
||||||
Assembly.Load("Mono.Posix, Version=2.0.0.0, Culture=neutral, " +
|
Assembly.Load("Mono.Posix, Version=2.0.0.0, Culture=neutral, " +
|
||||||
"PublicKeyToken=0738eb9f132ed756");
|
"PublicKeyToken=0738eb9f132ed756");
|
||||||
@ -201,18 +198,18 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
|
|
||||||
public static bool CpuidTx(uint index, uint ecxValue,
|
public static bool CpuidTx(uint index, uint ecxValue,
|
||||||
out uint eax, out uint ebx, out uint ecx, out uint edx,
|
out uint eax, out uint ebx, out uint ecx, out uint edx,
|
||||||
ulong threadAffinityMask) {
|
GroupAffinity affinity)
|
||||||
|
{
|
||||||
ulong mask = ThreadAffinity.Set(threadAffinityMask);
|
var previousAffinity = ThreadAffinity.Set(affinity);
|
||||||
|
|
||||||
if (mask == 0) {
|
if (previousAffinity == GroupAffinity.Undefined) {
|
||||||
eax = ebx = ecx = edx = 0;
|
eax = ebx = ecx = edx = 0;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Cpuid(index, ecxValue, out eax, out ebx, out ecx, out edx);
|
Cpuid(index, ecxValue, out eax, out ebx, out ecx, out edx);
|
||||||
|
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
License, v. 2.0. If a copy of the MPL was not distributed with this
|
License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
|
||||||
Copyright (C) 2012 Michael Möller <mmoeller@openhardwaremonitor.org>
|
Copyright (C) 2012-2020 Michael Möller <mmoeller@openhardwaremonitor.org>
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -13,9 +13,20 @@ using System.Diagnostics;
|
|||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
namespace OpenHardwareMonitor.Hardware {
|
namespace OpenHardwareMonitor.Hardware {
|
||||||
internal static class OperatingSystem {
|
public static class OperatingSystem {
|
||||||
|
|
||||||
public static bool Is64BitOperatingSystem() {
|
static OperatingSystem() {
|
||||||
|
int p = (int)Environment.OSVersion.Platform;
|
||||||
|
IsUnix = (p == 4) || (p == 6) || (p == 128);
|
||||||
|
|
||||||
|
Is64BitOperatingSystem = GetIs64BitOperatingSystem();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static bool IsUnix { get; }
|
||||||
|
|
||||||
|
public static bool Is64BitOperatingSystem { get; }
|
||||||
|
|
||||||
|
private static bool GetIs64BitOperatingSystem() {
|
||||||
if (IntPtr.Size == 8)
|
if (IntPtr.Size == 8)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
@ -18,8 +18,7 @@ namespace OpenHardwareMonitor.Hardware.RAM {
|
|||||||
public RAMGroup(SMBIOS smbios, ISettings settings) {
|
public RAMGroup(SMBIOS smbios, ISettings settings) {
|
||||||
|
|
||||||
// No implementation for RAM on Unix systems
|
// No implementation for RAM on Unix systems
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix) {
|
||||||
if ((p == 4) || (p == 128)) {
|
|
||||||
hardware = new Hardware[0];
|
hardware = new Hardware[0];
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -4,7 +4,7 @@
|
|||||||
License, v. 2.0. If a copy of the MPL was not distributed with this
|
License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
|
||||||
Copyright (C) 2010-2016 Michael Möller <mmoeller@openhardwaremonitor.org>
|
Copyright (C) 2010-2020 Michael Möller <mmoeller@openhardwaremonitor.org>
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@ -80,7 +80,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
|
|
||||||
private static bool ExtractDriver(string fileName) {
|
private static bool ExtractDriver(string fileName) {
|
||||||
string resourceName = "OpenHardwareMonitor.Hardware." +
|
string resourceName = "OpenHardwareMonitor.Hardware." +
|
||||||
(OperatingSystem.Is64BitOperatingSystem() ? "WinRing0x64.sys" :
|
(OperatingSystem.Is64BitOperatingSystem ? "WinRing0x64.sys" :
|
||||||
"WinRing0.sys");
|
"WinRing0.sys");
|
||||||
|
|
||||||
string[] names = GetAssembly().GetManifestResourceNames();
|
string[] names = GetAssembly().GetManifestResourceNames();
|
||||||
@ -129,8 +129,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
|
|
||||||
public static void Open() {
|
public static void Open() {
|
||||||
// no implementation for unix systems
|
// no implementation for unix systems
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if ((p == 4) || (p == 128))
|
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (driver != null)
|
if (driver != null)
|
||||||
@ -284,13 +283,13 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static bool RdmsrTx(uint index, out uint eax, out uint edx,
|
public static bool RdmsrTx(uint index, out uint eax, out uint edx,
|
||||||
ulong threadAffinityMask)
|
GroupAffinity affinity)
|
||||||
{
|
{
|
||||||
ulong mask = ThreadAffinity.Set(threadAffinityMask);
|
var previousAffinity = ThreadAffinity.Set(affinity);
|
||||||
|
|
||||||
bool result = Rdmsr(index, out eax, out edx);
|
bool result = Rdmsr(index, out eax, out edx);
|
||||||
|
|
||||||
ThreadAffinity.Set(mask);
|
ThreadAffinity.Set(previousAffinity);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -42,8 +42,7 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public SMBIOS() {
|
public SMBIOS() {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix) {
|
||||||
if ((p == 4) || (p == 128)) {
|
|
||||||
this.raw = null;
|
this.raw = null;
|
||||||
this.table = null;
|
this.table = null;
|
||||||
|
|
||||||
|
@ -184,8 +184,7 @@ namespace OpenHardwareMonitor.Hardware.TBalancer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static string GetDllName() {
|
private static string GetDllName() {
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
if (OperatingSystem.IsUnix)
|
||||||
if ((p == 4) || (p == 128))
|
|
||||||
return "libftd2xx.so";
|
return "libftd2xx.so";
|
||||||
else
|
else
|
||||||
return "ftd2xx.dll";
|
return "ftd2xx.dll";
|
||||||
|
@ -4,43 +4,109 @@
|
|||||||
License, v. 2.0. If a copy of the MPL was not distributed with this
|
License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||||
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||||
|
|
||||||
Copyright (C) 2010-2014 Michael Möller <mmoeller@openhardwaremonitor.org>
|
Copyright (C) 2010-2020 Michael Möller <mmoeller@openhardwaremonitor.org>
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
namespace OpenHardwareMonitor.Hardware {
|
namespace OpenHardwareMonitor.Hardware {
|
||||||
|
|
||||||
internal static class ThreadAffinity {
|
internal static class ThreadAffinity {
|
||||||
|
|
||||||
public static ulong Set(ulong mask) {
|
static ThreadAffinity() {
|
||||||
if (mask == 0)
|
ProcessorGroupCount = GetProcessorGroupCount();
|
||||||
return 0;
|
}
|
||||||
|
|
||||||
int p = (int)Environment.OSVersion.Platform;
|
private static int GetProcessorGroupCount() {
|
||||||
if ((p == 4) || (p == 128)) { // Unix
|
if (OperatingSystem.IsUnix)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
try {
|
||||||
|
return NativeMethods.GetActiveProcessorGroupCount();
|
||||||
|
} catch {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int ProcessorGroupCount { get; }
|
||||||
|
|
||||||
|
public static bool IsValid(GroupAffinity affinity) {
|
||||||
|
if (OperatingSystem.IsUnix) {
|
||||||
|
if (affinity.Group > 0)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
var previous = Set(affinity);
|
||||||
|
if (previous == GroupAffinity.Undefined)
|
||||||
|
return false;
|
||||||
|
Set(previous);
|
||||||
|
return true;
|
||||||
|
} catch {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Sets the processor group affinity for the current thread.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="affinity">The processor group affinity.</param>
|
||||||
|
/// <returns>The previous processor group affinity.</returns>
|
||||||
|
public static GroupAffinity Set(GroupAffinity affinity) {
|
||||||
|
if (affinity == GroupAffinity.Undefined)
|
||||||
|
return GroupAffinity.Undefined;
|
||||||
|
|
||||||
|
if (OperatingSystem.IsUnix) {
|
||||||
|
if (affinity.Group > 0)
|
||||||
|
throw new ArgumentOutOfRangeException("affinity.Group");
|
||||||
|
|
||||||
ulong result = 0;
|
ulong result = 0;
|
||||||
if (NativeMethods.sched_getaffinity(0, (IntPtr)Marshal.SizeOf(result),
|
if (NativeMethods.sched_getaffinity(0, (IntPtr)8, ref result) != 0)
|
||||||
ref result) != 0)
|
return GroupAffinity.Undefined;
|
||||||
return 0;
|
|
||||||
if (NativeMethods.sched_setaffinity(0, (IntPtr)Marshal.SizeOf(mask),
|
ulong mask = affinity.Mask;
|
||||||
ref mask) != 0)
|
if (NativeMethods.sched_setaffinity(0, (IntPtr)8, ref mask) != 0)
|
||||||
return 0;
|
return GroupAffinity.Undefined;
|
||||||
return result;
|
|
||||||
} else { // Windows
|
return new GroupAffinity(0, result);
|
||||||
|
} else {
|
||||||
UIntPtr uIntPtrMask;
|
UIntPtr uIntPtrMask;
|
||||||
try {
|
try {
|
||||||
uIntPtrMask = (UIntPtr)mask;
|
uIntPtrMask = (UIntPtr)affinity.Mask;
|
||||||
} catch (OverflowException) {
|
} catch (OverflowException) {
|
||||||
throw new ArgumentOutOfRangeException("mask");
|
throw new ArgumentOutOfRangeException("affinity.Mask");
|
||||||
}
|
}
|
||||||
return (ulong)NativeMethods.SetThreadAffinityMask(
|
|
||||||
NativeMethods.GetCurrentThread(), uIntPtrMask);
|
var groupAffinity = new NativeMethods.GROUP_AFFINITY {
|
||||||
}
|
Group = affinity.Group,
|
||||||
}
|
Mask = uIntPtrMask
|
||||||
|
};
|
||||||
|
|
||||||
|
var currentThread = NativeMethods.GetCurrentThread();
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (NativeMethods.SetThreadGroupAffinity(currentThread,
|
||||||
|
ref groupAffinity, out var previousGroupAffinity))
|
||||||
|
{
|
||||||
|
return new GroupAffinity(previousGroupAffinity.Group,
|
||||||
|
(ulong)previousGroupAffinity.Mask);
|
||||||
|
} else {
|
||||||
|
return GroupAffinity.Undefined;
|
||||||
|
}
|
||||||
|
} catch (EntryPointNotFoundException) {
|
||||||
|
if (affinity.Group > 0)
|
||||||
|
throw new ArgumentOutOfRangeException("affinity.Group");
|
||||||
|
|
||||||
|
var previous = (ulong)NativeMethods.SetThreadAffinityMask(
|
||||||
|
currentThread, uIntPtrMask);
|
||||||
|
|
||||||
|
return new GroupAffinity(0, previous);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static class NativeMethods {
|
private static class NativeMethods {
|
||||||
private const string KERNEL = "kernel32.dll";
|
private const string KERNEL = "kernel32.dll";
|
||||||
|
|
||||||
@ -49,8 +115,27 @@ namespace OpenHardwareMonitor.Hardware {
|
|||||||
SetThreadAffinityMask(IntPtr handle, UIntPtr mask);
|
SetThreadAffinityMask(IntPtr handle, UIntPtr mask);
|
||||||
|
|
||||||
[DllImport(KERNEL, CallingConvention = CallingConvention.Winapi)]
|
[DllImport(KERNEL, CallingConvention = CallingConvention.Winapi)]
|
||||||
public static extern IntPtr GetCurrentThread();
|
public static extern IntPtr GetCurrentThread();
|
||||||
|
|
||||||
|
[DllImport(KERNEL, CallingConvention = CallingConvention.Winapi)]
|
||||||
|
public static extern ushort GetActiveProcessorGroupCount();
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential, Pack = 4)]
|
||||||
|
public struct GROUP_AFFINITY {
|
||||||
|
public UIntPtr Mask;
|
||||||
|
[MarshalAs(UnmanagedType.U2)]
|
||||||
|
public ushort Group;
|
||||||
|
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 3,
|
||||||
|
ArraySubType = UnmanagedType.U2)]
|
||||||
|
public ushort[] Reserved;
|
||||||
|
}
|
||||||
|
|
||||||
|
[DllImport(KERNEL, CallingConvention = CallingConvention.Winapi)]
|
||||||
|
public static extern bool SetThreadGroupAffinity(
|
||||||
|
IntPtr thread,
|
||||||
|
ref GROUP_AFFINITY groupAffinity,
|
||||||
|
out GROUP_AFFINITY previousGroupAffinity);
|
||||||
|
|
||||||
private const string LIBC = "libc";
|
private const string LIBC = "libc";
|
||||||
|
|
||||||
[DllImport(LIBC)]
|
[DllImport(LIBC)]
|
||||||
|
@ -64,6 +64,7 @@
|
|||||||
<Compile Include="Hardware\Control.cs" />
|
<Compile Include="Hardware\Control.cs" />
|
||||||
<Compile Include="Hardware\CPU\AMD17CPU.cs" />
|
<Compile Include="Hardware\CPU\AMD17CPU.cs" />
|
||||||
<Compile Include="Hardware\FirmwareTable.cs" />
|
<Compile Include="Hardware\FirmwareTable.cs" />
|
||||||
|
<Compile Include="Hardware\GroupAffinity.cs" />
|
||||||
<Compile Include="Hardware\HDD\DebugSmart.cs" />
|
<Compile Include="Hardware\HDD\DebugSmart.cs" />
|
||||||
<Compile Include="Hardware\HDD\DriveAttributeValue.cs" />
|
<Compile Include="Hardware\HDD\DriveAttributeValue.cs" />
|
||||||
<Compile Include="Hardware\HDD\DriveThresholdValue.cs" />
|
<Compile Include="Hardware\HDD\DriveThresholdValue.cs" />
|
||||||
|
@ -10,5 +10,5 @@
|
|||||||
|
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
|
|
||||||
[assembly: AssemblyVersion("0.9.2.3")]
|
[assembly: AssemblyVersion("0.9.2.4")]
|
||||||
[assembly: AssemblyInformationalVersion("0.9.2.3 Alpha")]
|
[assembly: AssemblyInformationalVersion("0.9.2.4 Alpha")]
|
Loading…
x
Reference in New Issue
Block a user