Added support for W83627DHG chips. Changed Core i7 temperature reading. Fixed IT87 temperature reading.
1.1 --- a/Hardware/CPU/IntelCPU.cs Fri Jan 29 21:58:31 2010 +0000
1.2 +++ b/Hardware/CPU/IntelCPU.cs Sun Jan 31 19:30:00 2010 +0000
1.3 @@ -161,7 +161,7 @@
1.4 for (int i = 0; i < coreTemperatures.Length; i++) {
1.5 if (WinRing0.RdmsrPx(
1.6 IA32_THERM_STATUS_MSR, ref eax, ref edx,
1.7 - (UIntPtr)(logicalProcessorsPerCore << i)))
1.8 + (UIntPtr)(1 << (int)(logicalProcessorsPerCore * i))))
1.9 {
1.10 // if reading is valid
1.11 if ((eax & 0x80000000) != 0) {
2.1 --- a/Hardware/LPC/IT87.cs Fri Jan 29 21:58:31 2010 +0000
2.2 +++ b/Hardware/LPC/IT87.cs Sun Jan 31 19:30:00 2010 +0000
2.3 @@ -181,9 +181,9 @@
2.4 }
2.5
2.6 foreach (Sensor sensor in temperatures) {
2.7 - int value = ReadByte((byte)(TEMPERATURE_BASE_REG + sensor.Index));
2.8 + sbyte value = (sbyte)ReadByte((byte)(TEMPERATURE_BASE_REG + sensor.Index));
2.9 sensor.Value = value;
2.10 - if (value < 254)
2.11 + if (value < sbyte.MaxValue && value > 0)
2.12 ActivateSensor(sensor);
2.13 else
2.14 DeactivateSensor(sensor);
3.1 --- a/Hardware/LPC/LPCGroup.cs Fri Jan 29 21:58:31 2010 +0000
3.2 +++ b/Hardware/LPC/LPCGroup.cs Sun Jan 31 19:30:00 2010 +0000
3.3 @@ -63,7 +63,7 @@
3.4 private byte ReadByte(byte register) {
3.5 WinRing0.WriteIoPortByte(registerPort, register);
3.6 return WinRing0.ReadIoPortByte(valuePort);
3.7 - }
3.8 + }
3.9
3.10 private ushort ReadWord(byte register) {
3.11 return (ushort)((ReadByte(register) << 8) |
4.1 --- a/Hardware/LPC/W83627DHG.cs Fri Jan 29 21:58:31 2010 +0000
4.2 +++ b/Hardware/LPC/W83627DHG.cs Sun Jan 31 19:30:00 2010 +0000
4.3 @@ -14,12 +14,79 @@
4.4 private bool available = false;
4.5 private ushort address;
4.6
4.7 + private List<ISensor> active = new List<ISensor>();
4.8 +
4.9 + private Sensor[] temperatures;
4.10 + private Sensor[] fans;
4.11 + private Sensor[] voltages;
4.12 +
4.13 + private float[] voltageGains;
4.14 +
4.15 + // Consts
4.16 + private const ushort WINBOND_VENDOR_ID = 0x5CA3;
4.17 + private const byte HIGH_BYTE = 0x80;
4.18 +
4.19 + // Hardware Monitor
4.20 + private const byte ADDRESS_REGISTER_OFFSET = 0x05;
4.21 + private const byte DATA_REGISTER_OFFSET = 0x06;
4.22 +
4.23 + // Hardware Monitor Registers
4.24 + private const byte VOLTAGE_BASE_REG = 0x20;
4.25 + private const byte BANK_SELECT_REGISTER = 0x04E;
4.26 + private const byte VENDOR_ID_REGISTER = 0x4F;
4.27 + private const byte FIRST_BANK_REGISTER = 0x50;
4.28 + private const byte TEMPERATURE_BASE_REG = 0x50;
4.29 + private const byte TEMPERATURE_SYS_REG = 0x27;
4.30 +
4.31 + private byte[] FAN_TACHO_REG = new byte[] { 0x28, 0x29, 0x2A, 0x3F, 0x53 };
4.32 + private byte[] FAN_TACHO_BANK = new byte[] { 0, 0, 0, 0, 5 };
4.33 + private string[] FAN_NAME = new string[]
4.34 + { "System", "CPU #1", "Auxiliary #1", "CPU #2", "Auxiliary #2" };
4.35 + private byte[] FAN_BIT_REG = new byte[] { 0x47, 0x4B, 0x4C, 0x59, 0x5D };
4.36 + private byte[] FAN_DIV_BIT0 = new byte[] { 36, 38, 30, 8, 10 };
4.37 + private byte[] FAN_DIV_BIT1 = new byte[] { 37, 39, 31, 9, 11 };
4.38 + private byte[] FAN_DIV_BIT2 = new byte[] { 5, 6, 7, 23, 15 };
4.39 +
4.40 + private byte ReadByte(byte bank, byte register) {
4.41 + WinRing0.WriteIoPortByte(
4.42 + (ushort)(address + ADDRESS_REGISTER_OFFSET), BANK_SELECT_REGISTER);
4.43 + WinRing0.WriteIoPortByte(
4.44 + (ushort)(address + DATA_REGISTER_OFFSET), bank);
4.45 + WinRing0.WriteIoPortByte(
4.46 + (ushort)(address + ADDRESS_REGISTER_OFFSET), register);
4.47 + return WinRing0.ReadIoPortByte(
4.48 + (ushort)(address + DATA_REGISTER_OFFSET));
4.49 + }
4.50 +
4.51 public W83627DHG(byte revision, ushort address) {
4.52 this.revision = revision;
4.53 this.address = address;
4.54
4.55 + // Check vendor id
4.56 + ushort vendorId =
4.57 + (ushort)((ReadByte(HIGH_BYTE, VENDOR_ID_REGISTER) << 8) |
4.58 + ReadByte(0, VENDOR_ID_REGISTER));
4.59 + if (vendorId != WINBOND_VENDOR_ID)
4.60 + return;
4.61 +
4.62 + voltageGains = new float[] { 0.008f, 1, 1, 0.016f, 1, 1, 1, 0.016f };
4.63 + voltages = new Sensor[3];
4.64 + voltages[0] = new Sensor("CPU VCore", 0, SensorType.Voltage, this);
4.65 + voltages[1] = new Sensor("+3.3V", 3, SensorType.Voltage, this);
4.66 + voltages[2] = new Sensor("Battery", 7, SensorType.Voltage, this);
4.67 +
4.68 + temperatures = new Sensor[3];
4.69 + temperatures[0] = new Sensor("CPU", 0, SensorType.Temperature, this);
4.70 + temperatures[1] = new Sensor("Auxiliary", 1, SensorType.Temperature, this);
4.71 + temperatures[2] = new Sensor("System", 2, SensorType.Temperature, this);
4.72 +
4.73 + fans = new Sensor[FAN_NAME.Length];
4.74 + for (int i = 0; i < FAN_NAME.Length; i++)
4.75 + fans[i] = new Sensor(FAN_NAME[i], i, SensorType.Fan, this);
4.76 +
4.77 this.name = "Winbond W83627DHG";
4.78 this.icon = Utilities.EmbeddedResources.GetImage("chip.png");
4.79 + available = true;
4.80 }
4.81
4.82 public bool IsAvailable {
4.83 @@ -39,7 +106,7 @@
4.84 }
4.85
4.86 public ISensor[] Sensors {
4.87 - get { return new ISensor[0]; }
4.88 + get { return active.ToArray(); }
4.89 }
4.90
4.91 public string GetReport() {
4.92 @@ -50,15 +117,103 @@
4.93 r.Append("Chip revision: 0x"); r.AppendLine(revision.ToString("X"));
4.94 r.Append("Base Adress: 0x"); r.AppendLine(address.ToString("X4"));
4.95 r.AppendLine();
4.96 + r.AppendLine("Hardware Monitor Registers");
4.97 + r.AppendLine();
4.98 + r.AppendLine(" 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F");
4.99 + r.AppendLine();
4.100 + for (int i = 0; i < 0x7; i++) {
4.101 + r.Append(" "); r.Append((i << 4).ToString("X2")); r.Append(" ");
4.102 + for (int j = 0; j <= 0xF; j++) {
4.103 + r.Append(" ");
4.104 + r.Append(ReadByte(0, (byte)((i << 4) | j)).ToString("X2"));
4.105 + }
4.106 + r.AppendLine();
4.107 + }
4.108 + for (int k = 1; k <=5; k++) {
4.109 + r.AppendLine("Bank " + k);
4.110 + for (int i = 0x5; i < 0x6; i++) {
4.111 + r.Append(" "); r.Append((i << 4).ToString("X2")); r.Append(" ");
4.112 + for (int j = 0; j <= 0xF; j++) {
4.113 + r.Append(" ");
4.114 + r.Append(ReadByte((byte)(k),
4.115 + (byte)((i << 4) | j)).ToString("X2"));
4.116 + }
4.117 + r.AppendLine();
4.118 + }
4.119 + }
4.120 + r.AppendLine();
4.121
4.122 return r.ToString();
4.123 }
4.124
4.125 - public void Update() { }
4.126 + public void Update() {
4.127 + foreach (Sensor sensor in voltages) {
4.128 + if (sensor.Index < 7) {
4.129 + int value = ReadByte(0, (byte)(VOLTAGE_BASE_REG + sensor.Index));
4.130 + sensor.Value = voltageGains[sensor.Index] * value;
4.131 + if (sensor.Value > 0)
4.132 + ActivateSensor(sensor);
4.133 + else
4.134 + DeactivateSensor(sensor);
4.135 + } else {
4.136 + // Battery voltage
4.137 + bool valid = (ReadByte(0, 0x5D) & 0x01) > 0;
4.138 + if (valid) {
4.139 + sensor.Value = voltageGains[sensor.Index] *
4.140 + ReadByte(5, 0x51);
4.141 + ActivateSensor(sensor);
4.142 + } else
4.143 + DeactivateSensor(sensor);
4.144 + }
4.145 + }
4.146
4.147 - #pragma warning disable 67
4.148 + foreach (Sensor sensor in temperatures) {
4.149 + int value;
4.150 + if (sensor.Index < 2) {
4.151 + value = ReadByte((byte)(sensor.Index + 1), TEMPERATURE_BASE_REG);
4.152 + value = (value << 1) | ReadByte((byte)(sensor.Index + 1),
4.153 + (byte)(TEMPERATURE_BASE_REG + 1)) >> 7;
4.154 + } else {
4.155 + value = ReadByte(0, TEMPERATURE_SYS_REG) << 1;
4.156 + }
4.157 + sensor.Value = value / 2.0f;
4.158 + if (value < 0x1FE)
4.159 + ActivateSensor(sensor);
4.160 + else
4.161 + DeactivateSensor(sensor);
4.162 + }
4.163 +
4.164 + long bits = 0;
4.165 + for (int i = 0; i < FAN_BIT_REG.Length; i++)
4.166 + bits = (bits << 8) | ReadByte(0, FAN_BIT_REG[i]);
4.167 + foreach (Sensor sensor in fans) {
4.168 + int count = ReadByte(FAN_TACHO_BANK[sensor.Index],
4.169 + FAN_TACHO_REG[sensor.Index]);
4.170 + int divisorBits = (int)(
4.171 + (((bits >> FAN_DIV_BIT2[sensor.Index]) & 1) << 2) |
4.172 + (((bits >> FAN_DIV_BIT1[sensor.Index]) & 1) << 1) |
4.173 + ((bits >> FAN_DIV_BIT0[sensor.Index]) & 1));
4.174 + int divisor = 1 << divisorBits;
4.175 + sensor.Value = (count < 0xff) ? 1.35e6f / (count * divisor) : 0;
4.176 + ActivateSensor(sensor);
4.177 + }
4.178 + }
4.179 +
4.180 + private void ActivateSensor(Sensor sensor) {
4.181 + if (!active.Contains(sensor)) {
4.182 + active.Add(sensor);
4.183 + SensorAdded(sensor);
4.184 + }
4.185 + }
4.186 +
4.187 + private void DeactivateSensor(Sensor sensor) {
4.188 + if (active.Contains(sensor)) {
4.189 + active.Remove(sensor);
4.190 + SensorRemoved(sensor);
4.191 + }
4.192 + }
4.193 +
4.194 public event SensorEventHandler SensorAdded;
4.195 public event SensorEventHandler SensorRemoved;
4.196 - #pragma warning restore 67
4.197 }
4.198 }