Esempio n. 1
0
/* reads values for thermal_zone num, return 0 on success, negative values on error */
int
read_acpi_zone(const int num, global_t *globals){
	char *buf = NULL;
	char *tmp = NULL;
	thermal_t *info = &thermals[num];

	if(num > MAX_ITEMS) return ITEM_EXCEED;

	/* scan state file */
	if((buf = get_acpi_content(info->state_file)) == NULL)
		info->therm_state = T_ERR;

	if(buf && (tmp = scan_acpi_value(buf, "state:")))
			thermal_state(tmp, info);
	free(tmp);
	free(buf);

	/* scan temperature file */
	if((buf = get_acpi_content(info->temp_file)) == NULL)
		info->temperature = NOT_SUPPORTED;

	if(buf && (tmp = scan_acpi_value(buf, "temperature:"))){
		info->temperature = strtol(tmp, NULL, 10);
		/* if we just have one big thermal zone, this will be the global temperature */
		if(globals->thermal_count == 1)
			globals->temperature = info->temperature;
	}
	free(tmp);
	free(buf);

	/* scan cooling mode file */
	if((buf = get_acpi_content(info->cooling_file)) == NULL)
		info->therm_mode = CO_ERR;
	if(buf && (tmp = scan_acpi_value(buf, "cooling mode:")))
		fill_cooling_mode(tmp, info);
	else info->therm_mode = CO_ERR;
	free(tmp);
	free(buf);

	/* scan polling_frequencies file */
	if((buf = get_acpi_content(info->freq_file)) == NULL)
		info->frequency = DISABLED;
	if(buf && (tmp = scan_acpi_value(buf, "polling frequency:")))
		info->frequency = strtol(tmp, NULL, 10);
	else info->frequency = DISABLED;
	free(tmp);
	free(buf);

	/* TODO: IMPLEMENT TRIP POINTS FILE */

	return SUCCESS;
}
Esempio n. 2
0
/* returns the acpi version or NOT_SUPPORTED(negative value) on failure */
static int
get_acpi_version(void){
	long ret = -1;
	char *tmp = get_acpi_content(PROC_ACPI "info");
	char *version = NULL;
	
	if(!tmp) {
		tmp = get_acpi_content("/sys/module/acpi/parameters/acpica_version");
		if (tmp) {
			long ret = strtol(tmp, NULL, 10);
			free(tmp);
			return ret;
		} else {
			return NOT_SUPPORTED;
		}
	}
	if((version = scan_acpi_value(tmp, "version:")) == NULL){
		free(tmp);
		return NOT_SUPPORTED;
	}
	ret = strtol(version, NULL, 10);
	free(tmp);
	free(version);
	return ret;
}
Esempio n. 3
0
/* read alarm capacity, return 0 on success, negative values on error */
static int
read_acpi_battalarm(const int num, const int sysstyle){
	char *buf = NULL;
	char *tmp = NULL;
	battery_t *info = &batteries[num];

	if((buf = get_acpi_content(info->alarm_file)) == NULL)
		return NOT_SUPPORTED;

	if(sysstyle)
	{
		if(!strcmp(buf, "0"))
			info->alarm = 0;
		else if(!strcmp(buf, "1"))
			info->alarm = 1;
		else
			info->alarm = NOT_SUPPORTED;
	}
	else
	{
		if((tmp = scan_acpi_value(buf, "alarm:")) && tmp[0] != 'u')
			info->alarm = strtol(tmp, NULL, 10);
		else
			info->alarm = NOT_SUPPORTED;
	}
	free(buf);
	free(tmp);
	return SUCCESS;
}
Esempio n. 4
0
/* reads the acpi state and writes it into the globals structure, void */
void
read_acpi_acstate(global_t *globals){
	adapter_t *ac = &globals->adapt;
	char *buf = NULL;
	char *tmp = NULL;

	if(ac->state_file && (buf = get_acpi_content(ac->state_file)) == NULL){
		ac->ac_state = P_ERR;
		return;
	}
	if(globals->sysstyle)
	{
		if(!strcmp(buf, "1"))
			ac->ac_state = P_AC;
		else if(!strcmp(buf, "0"))
			ac->ac_state = P_BATT;
		else ac->ac_state = P_ERR;
	}
	else
	{
		if((tmp = scan_acpi_value(buf, "state:")) && !strncmp(tmp, "on-line", 7))
			ac->ac_state = P_AC;
		else if(tmp && !strncmp(tmp, "off-line", 8))
			ac->ac_state = P_BATT;
		else ac->ac_state = P_ERR;
	}
	free(buf);
	free(tmp);
}
Esempio n. 5
0
/* read acpi information for fan num, returns 0 on success and negative values on errors */
int
read_acpi_fan(const int num){
	char *buf = NULL;
	char *tmp = NULL;
	fan_t *info = &fans[num];

	if(num > MAX_ITEMS) return ITEM_EXCEED;

	/* scan state file */
	if((buf = get_acpi_content(info->state_file)) == NULL)
		info->fan_state = F_ERR;

	if(!buf || (tmp = scan_acpi_value(buf, "status:")) == NULL){
		info->fan_state = F_ERR;
		return NOT_SUPPORTED;
	}
	if (tmp[0] == 'o' && tmp[1] == 'n') info->fan_state = F_ON;
	else if(tmp[0] == 'o' && tmp[1] == 'f') info->fan_state = F_OFF;
	else info->fan_state = F_ERR;
	free(buf);
	free(tmp);
	return SUCCESS;
}
Esempio n. 6
0
/* reads static values for a battery (info file), returns SUCCESS */
static int
read_acpi_battinfo(const int num, const int sysstyle){
	char *buf = NULL;
	char *tmp = NULL;
	battery_t *info = &batteries[num];
	int i = 0;
	char sysfile[MAX_NAME];

	if(sysstyle)
	{
		snprintf(sysfile, MAX_NAME, "%s/present", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		if(!strcmp(buf, "1")) {
			info->present = 1;
		} else {
			info->present = 0;
			return NOT_PRESENT;
		}
        free(buf);

		snprintf(sysfile, MAX_NAME, "%s/charge_full_design", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->design_cap = strtol(buf, NULL, 10);
        free(buf);

		snprintf(sysfile, MAX_NAME, "%s/charge_full", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->last_full_cap = strtol(buf, NULL, 10);
        free(buf);

		snprintf(sysfile, MAX_NAME, "%s/charge_now", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->remaining_cap = strtol(buf, NULL, 10);
        free(buf);

		snprintf(sysfile, MAX_NAME, "%s/voltage_min_design", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->design_voltage = strtol(buf, NULL, 10);
        free(buf);

		snprintf(sysfile, MAX_NAME, "%s/voltage_now", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->present_voltage = strtol(buf, NULL, 10);
        free(buf);

		/* FIXME: is rate == current here? */
		snprintf(sysfile, MAX_NAME, "%s/current_now", info->info_file);
		if((buf = get_acpi_content(sysfile)) == NULL)
			return NOT_SUPPORTED;
		info->present_rate = strtol(buf, NULL, 10);
        free(buf);

		return SUCCESS;
	}

	if((buf = get_acpi_content(info->info_file)) == NULL)
		return NOT_SUPPORTED;

	/* you have to read the present value always since a battery can be taken away while
	 * refreshing the data */
	if((tmp = scan_acpi_value(buf, "present:")) && !strncmp(tmp, "yes", 3)) {
		free(tmp);
		info->present = 1;
	} else {
		info->present = 0;
		free(buf);
		return NOT_PRESENT;
	}

	if((tmp = scan_acpi_value(buf, "design capacity:")) && tmp[0] != 'u'){
		info->design_cap = strtol(tmp, NULL, 10);
		/* workaround ACPI's broken way of reporting no battery */
		if(info->design_cap == 655350) info->design_cap = NOT_SUPPORTED;
		free(tmp);
	}
	else info->design_cap = NOT_SUPPORTED;

	for (;battinfo_values[i].value; i++) {
		if ((tmp = scan_acpi_value(buf, battinfo_values[i].value)) && tmp[0] != 'u') {
			*((int *)(((char *)info) + battinfo_values[i].offset)) = strtol(tmp, NULL, 10);
			free(tmp);
		} else {
			*((int *)(((char *)info) + battinfo_values[i].offset)) = NOT_SUPPORTED;
		}
	}

	/* TODO remove debug */
	/* printf("%s\n", buf); */
	free(buf);

	return SUCCESS;
}
Esempio n. 7
0
/* Read ACPI info on a given power adapter and battery, and fill the passed
 * apm_info struct. */
int acpi_read (int battery, apm_info *info) {
	char *buf, *state;
	
	if (acpi_batt_count == 0) {
		info->battery_percentage = 0;
		info->battery_time = 0;
		info->battery_status = BATTERY_STATUS_ABSENT;
		acpi_batt_capacity[battery] = 0;
		/* Where else would the power come from, eh? ;-) */
		info->ac_line_status = 1;
		return 0;
	}
	
	/* Internally it's zero indexed. */
	battery--;
	
	buf = get_acpi_file(acpi_batt_info[battery]);
	if (buf == NULL) {
		fprintf(stderr, "unable to read %s\n", acpi_batt_info[battery]);
		perror("read");
		exit(1);
	}

	info->ac_line_status = 0;
	info->battery_flags = 0;
	info->using_minutes = 1;
	
	/* Work out if the battery is present, and what percentage of full
	 * it is and how much time is left. */
	if (strcmp(scan_acpi_value(buf, acpi_labels[label_present]), "1") == 0) {
		int pcap = scan_acpi_num(buf, acpi_labels[label_remaining_capacity]);
		int rate = scan_acpi_num(buf, acpi_labels[label_present_rate]);
		if (rate) {
			/* time remaining = (current_capacity / discharge rate) */
			info->battery_time = (float) pcap / (float) rate * 60;
		}
		else {
			char *rate_s = scan_acpi_value(buf, acpi_labels[label_present_rate]);
			if (! rate_s) {
				/* Time remaining unknown. */
				info->battery_time = 0;
			}
			else {
				/* a zero or unknown in the file; time 
				 * unknown so use a negative one to
				 * indicate this */
				info->battery_time = -1;
			}
		}

		state = scan_acpi_value(buf, acpi_labels[label_charging_state]);
		if (state) {
			if (state[0] == 'D') { /* discharging */
				info->battery_status = BATTERY_STATUS_CHARGING;
				/* Expensive ac power check used here
				 * because AC power might be on even if a
				 * battery is discharging in some cases. */
				info->ac_line_status = on_ac_power();
			}
			else if (state[0] == 'C' && state[1] == 'h') { /* charging */
				info->battery_status = BATTERY_STATUS_CHARGING;
				info->ac_line_status = 1;
				info->battery_flags = info->battery_flags | BATTERY_FLAGS_CHARGING;
				if (rate)
					info->battery_time = -1 * (float) (acpi_batt_capacity[battery] - pcap) / (float) rate * 60;
				else
					info->battery_time = 0;
				if (abs(info->battery_time) < 0.5)
					info->battery_time = 0;
			}
			else if (state[0] == 'F') { /* full */
				/* charged, on ac power */
				info->battery_status = BATTERY_STATUS_HIGH;
				info->ac_line_status = 1;
			}
			else if (state[0] == 'C') { /* not charging, so must be critical */
				info->battery_status = BATTERY_STATUS_CRITICAL;
				/* Expensive ac power check used here
				 * because AC power might be on even if a
				 * battery is critical in some cases. */
				info->ac_line_status = on_ac_power();
			}
			else if (state[0] == 'U') { /* unknown */
				info->ac_line_status = on_ac_power();
				int current = scan_acpi_num(buf, acpi_labels[label_present_rate]);
				if (info->ac_line_status) {
					if (current == 0)
						info->battery_status = BATTERY_STATUS_HIGH;
					else
						info->battery_status = BATTERY_STATUS_CHARGING;
				}
				else {
					info->battery_status = BATTERY_STATUS_CHARGING;
				}
			}
			else {
				fprintf(stderr, "unknown battery state: %s\n", state);
			}
		}
		else {
			/* Battery state unknown. */
			info->battery_status = BATTERY_STATUS_ABSENT;
		}

		if (acpi_batt_capacity[battery] == 0) {
			/* The battery was absent, and now is present.
			 * Well, it might be a different battery. So
			 * re-probe the battery. */
			/* NOTE that this invalidates buf. No accesses of
			 * buf below this point! */
			acpi_batt_capacity[battery] = get_acpi_batt_capacity(battery);
		}
		else if (pcap > acpi_batt_capacity[battery]) {
			/* Battery is somehow charged to greater than max
			 * capacity. Rescan for a new max capacity. */
			find_batteries();
		}

		if (pcap && acpi_batt_capacity[battery]) {
			info->battery_percentage = (long) 100 * pcap / acpi_batt_capacity[battery];
			if (info->battery_percentage > 100)
				info->battery_percentage = 100;
		}
		else {
			info->battery_percentage = -1;
		}

	}
	else {
		info->battery_percentage = 0;
		info->battery_time = 0;
		info->battery_status = BATTERY_STATUS_ABSENT;
		acpi_batt_capacity[battery] = 0;
		if (acpi_batt_count == 0) {
			/* Where else would the power come from, eh? ;-) */
			info->ac_line_status = 1;
		}
		else {
			/* Expensive ac power check. */
			info->ac_line_status = on_ac_power();
		}
	}
	
	return 0;
}
Esempio n. 8
0
/* Read an ACPI proc file, pull out the requested piece of information, and
 * return it (statically allocated string). Returns NULL on error, This is 
 * the slow, dumb way, fine for initialization or if only one value is needed
 * from a file, slow if called many times. */
char *get_acpi_value (const char *file, const char *key) {
	char *buf = get_acpi_file(file);
	if (! buf) return NULL;
	return scan_acpi_value(buf, key);
}