📄 fanstuff.cpp
字号:
// --------------------------------------------------------------
//
// Thinkpad Fan Control
//
// --------------------------------------------------------------
//
// This program and source code is in the public domain.
//
// The author claims no copyright, copyleft, license or
// whatsoever for the program itself (with exception of
// WinIO driver). You may use, reuse or distribute it's
// binaries or source code in any desired way or form,
// Useage of binaries or source shall be entirely and
// without exception at your own risk.
//
// --------------------------------------------------------------
#include "fancontrol.h"
#define TP_ECOFFSET_FAN (char)0x2F // 1 byte (binary xyzz zzz)
#define TP_ECOFFSET_FANSPEED (char)0x84 // 16 bit word, lo/hi byte
#define TP_ECOFFSET_TEMP0 (char)0x78 // 8 temp sensor bytes from here
#define TP_ECOFFSET_TEMP1 (char)0xC0 // 4 temp sensor bytes from here
#define PRTC_Write_Quick (char)0x02
#define PRTC_Read_Quick (char)0x03
#define PRTC_Send_Byte (char)0x04
#define PRTC_Receive_Byte (char)0x05
#define PRTC_Write_Byte (char)0x06
#define PRTC_Read_Byte (char)0x07
#define PRTC_Write_Word (char)0x08
#define PRTC_Read_Word (char)0x09
#define PRTC_Write_Block (char)0x0a
#define PRTC_Read_Block (char)0x0b
#define PRTC_Process_Call (char)0x0c
#define BATTERY_ADDRESS_IN_EC_SMBUS (char)0x0b
#define CMD_ManufacturerAccess (char)0x00
/*Remaining Capacity Alarm Threshold . mAh r/w */
#define CMD_RemainingCapacityAlarm (char)0x01
/*Remaining Time Alarm Threshold. minutes r/w */
#define CMD_RemainingTimeAlarm (char)0x02
/* Battery Operational Modes. Bit flags r/w */
#define CMD_BatteryMode (char)0x03
/*This function is the first half of a two-function call-set used to set the AtRate mA r/w 0
#define CMD_value used in calculations made by the AtRateTimeToFull(),
#define CMD_AtRateTimeToEmpty(), and AtRateOK() functions.*/
#define CMD_AtRate (char)0x04
/*Returns the predicted remaining time to fully charge the battery at the minutes r 65535
#define CMD_AtRate() value. */
#define CMD_AtRateTimeToFull (char)0x05
/*Returns the predicted remaining operating time if the battery is discharged minutes r 65535
at the AtRate() value. */
#define CMD_AtRateTimeToEmpty (char)0x06
/*Returns a Boolean value that indicates whether or not the battery can deliver boolean r 1
the AtRate value of additional energy for 10 seconds. If the AtRate() value is
zero or positive, the AtRateOK() function will ALWAYS return TRUE. */
#define CMD_AtRateOK (char)0x07
/*Returns the pack’s internal temperature. 0.1 K r */
#define CMD_Temperature (char)0x08
/*Returns the battery’s voltage (measured at the cell stack) mV r */
#define CMD_Voltage (char)0x09
/*Returns the current being supplied (or accepted) through the battery’s mA r terminals. */
#define CMD_Current (char)0x0a
/*Returns a rolling average based upon the last 64 samples of current. mA r */
#define CMD_AverageCurrent (char)0x0b
/* Returns the expected margin of error. percent r 10 *
#define CMD_MaxError (char)0x0c
/*Returns the predicted remaining battery capacity expressed as a percent r 0
percentage of FullChargeCapacity(). */
#define CMD_RelativeStateOfCharge (char)0x0d
/* Returns the predicted remaining battery capacity expressed as a percent r
percentage of DesignCapacity(). */
#define CMD_AbsoluteStateOfCharge (char)0x0e
/*Returns the predicted remaining battery capacity. mAh r */
#define CMD_RemainingCapacity (char)0x0f
/*Returns the predicted battery capacity when fully charged. mAh r */
#define CMD_FullChargeCapacity (char)0x10
/*Returns the predicted remaining battery life at the present rate of minutes r discharge. */
#define CMD_RunTimeToEmpty (char)0x11
/*Returns the rolling average of the predicted remaining battery life. minutes r *
#define CMD_AverageTimeToEmpty (char)0x12
/*Returns the rolling average of the predicted remaining time until the battery minutes r 65535
reaches full charge. */
#define CMD_AverageTimeToFull (char)0x13
/*Returns the battery’s desired charging rate. mA r */
#define CMD_ChargingCurrent (char)0x14
/*Returns the battery’s desired charging voltage. mV r */
#define CMD_ChargingVoltage (char)0x15
/*Returns the battery’s status word. Bit flags r */
#define CMD_BatteryStatus (char)0x16
/*Returns the number of charge/discharge cycles the battery has cycles r 0
experienced. A charge/discharge cycle is defined as “starting from a base
value equivalent to the battery’s highest SOC reached after the battery is no
longer accepting current before the present charge/discharge cycle is
complete and ending when the battery starts accepting current and its SOC
has decreased by 15% or more from that base value.” */
#define CMD_CycleCount (char)0x17
/*Returns the theoretical capacity of the new battery. mAh r */
#define CMD_DesignCapacity (char)0x18
/*Returns the theoretical voltage of a new battery. mV r */
#define CMD_DesignVoltage (char)0x19
/*Returns the version number of the SBDS the battery pack supports, as well Formatted r 0x0010
as voltage and current scaling information. word */
#define CMD_SpecificationInfo (char)0x1a
/*Returns the date the electronics were manufactured. Formatted r
word */
#define CMD_ManufacturerDate (char)0x1b
/* Returns the electronics serial number. number r /*
#define CMD_SerialNumber (char)0x1c
/*Returns a character array containing the manufacture’s name. string */
#define CMD_ManufacturerName (char)0x20
/*Returns a character array that contains the battery’s name. string */
#define CMD_DeviceName (char)0x21
/*Returns a character array that contains the battery’s chemistry. string */
#define CMD_DeviceChemistry (char)0x22
/*Returns data specific to the manufacture. */
#define CMD_ManufacturerData (char)0x23
// Thanks for the following to "Thinker" on
// http://www.thinkwiki.org/wiki/Talk:ACPI_fan_control_script
const char *gSensorNames[]= {
// 78-7F (state index 0-7)
"CPU", // main processor
"APS", // harddisk protection gyroscope
"PCM", // under PCMCIA slot (front left)
"GPU", // graphical processor
"BAT", // inside T43 battery
"X7D", // usually n/a
"BAT", // inside T43 battery
"X7F", // usually n/a
// C0-C4 (state index 8-11)
"BUS", // unknown
"PCI", // mini-pci, WLAN, southbridge area
"PWR", // power supply (get's hot while charging battery)
"XC3", // usually n/a
// future
"",
"",
"",
"",
""
};
//-------------------------------------------------------------------------
// switch fan according to settings
//-------------------------------------------------------------------------
int
FANCONTROL::HandleData(void)
{
char obuf[256]= "", obuf2[128]="",
templist[256]= "", templist2[512],
manlevel[16]= "", title2[128]= "";
int i, maxtemp, ok= 0;
char ReturnLen, ReturnData[32];
int status;
//
// determine highest temp.
//
// build a list of sensors to ignore, separated by "|", e.g. "|XC1|BAT|CPU|"
char what[16], list[128];
sprintf(list, "|%s|", this->IgnoreSensors);
for (i= 0; list[i]!='\0'; i++) {
if (list[i]==',')
list[i]= '|';
}
maxtemp= 0;
for (i= 0; i<12; i++) {
sprintf(what, "|%s|", this->State.SensorName[i]); // name (e.g. "|CPU|") to match against list above
if (this->State.Sensors[i]!=0x80 && this-State.Sensors[i]!=0x00 && strstr(list, what)==0) {
maxtemp= __max(this->State.Sensors[i], maxtemp);
}
}
this->MaxTemp= maxtemp;
//
// update dialog elements
//
// title string (for minimized window)
sprintf(title2, "%d癈", this->MaxTemp);
::GetDlgItemText(this->hwndDialog, 8310, manlevel, sizeof(manlevel));
if( strlen(manlevel) == 2)
{
for( i = 0 ; i < 2 ; i++)
{
if(manlevel[i] > 0x39)
manlevel[i] -= 0x37 ;
else
manlevel[i] -= 0x30 ;
}
this->ECSMBusBaseOffsetInERAM = manlevel[0] * 16 + manlevel[1];
}
else
this->ECSMBusBaseOffsetInERAM = 0xff;
/*
// display fan statte
int fanctrl= this->State.FanCtrl;
sprintf(obuf2, "0x%02x (", fanctrl);
if (fanctrl & 0x80) {
strcat(obuf2, "BIOS Controlled)");
strcat(title2, " Default Fan");
}
else {
sprintf(obuf2+strlen(obuf2), "Fan Level %d, Non Bios)", fanctrl & 0x3F);
sprintf(title2+strlen(title2), " Fan %d (%s)",
fanctrl & 0x3F,
this->CurrentModeFromDialog()==2 ? "Smart" : "Fixed");
}
::SetDlgItemText(this->hwndDialog, 8100, obuf2);
strcpy(this->Title2, title2);
// display fan speed (experimental, not visible)
int fanspeed= (this->State.FanSpeedHi << 8) | this->State.FanSpeedLo;
if (fanspeed && (short)fanspeed!=(short)0xffff)
sprintf(obuf2, "%d RPM", fanspeed);
else
strcpy(obuf2, "off");
::SetDlgItemText(this->hwndDialog, 8102, obuf2);
// display temperature list
sprintf(obuf2, "%d癈", this->MaxTemp);
::SetDlgItemText(this->hwndDialog, 8103, obuf2);
strcpy(templist2, "");
for (i= 0; i<12; i++) {
int temp= this->State.Sensors[i];
if (temp!=128) {
sprintf(obuf2, "%d癈", temp);
sprintf(templist2+strlen(templist2), "%s %s (0x%02x)",
this->State.SensorName[i],
obuf2,
this->State.SensorAddr[i]);
strcat(templist2, "\r\n");
}
else {
// strcat(templist2, "n/a\r\n");
}
}
::SetDlgItemText(this->hwndDialog, 8101, templist2);
*/
/* 检查为有效的基地址,才开始操作, 0xff表示无效的基地址 */
if ( this->ECSMBusBaseOffsetInERAM != 0xff)
{
if (this->HasReadDeviceName == FALSE)
{
// compact single line status (combined)
strcpy(templist, "Dev:");
/* for (i= 0; i<12; i++) {
if (this->State.Sensors[i]!=128) {
sprintf(templist+strlen(templist), "%d ", this->State.Sensors[i]);
}
else {
strcat(templist, "n/a ");
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -