all repos — tint2 @ 89f26595b6215eab389cb2cfff68f9a70392e862

fork of the tint2 desktop panel for my custom setup - only minimized windows across all desktops for the taskbar

support missing power usage data

Some notebooks do not provide power usage data. This code tries
to estimate the current power usage by measuring the battery level
difference in a specific time interval.
Sebastian Reichel sre@ring0.de
commit

89f26595b6215eab389cb2cfff68f9a70392e862

parent

3d39da9330f7bb44c82cbd7ecb1d529cc99b0d10

1 files changed, 26 insertions(+), 3 deletions(-)

jump to
M src/battery/linux.csrc/battery/linux.c

@@ -34,6 +34,7 @@

struct psy_battery { /* generic properties */ gchar* name; + gint64 timestamp; /* sysfs files */ gchar* path_present; gchar* path_energy_now;

@@ -280,17 +281,31 @@

return batteries != NULL; } +static gint estimate_power_usage(struct psy_battery *bat, gint old_energy_now, gint64 old_timestamp) { + gint64 diff_power = ABS(bat->energy_now - old_energy_now); + gint64 diff_time = bat->timestamp - old_timestamp; + + /* µW = (µWh * 3600) / (µs * 1000000) */ + gint power = diff_power * 3600 * 1000000 / diff_time; + + return power; +} + static gboolean update_linux_battery(struct psy_battery *bat) { GError *error = NULL; gchar *data; gsize datalen; + gint64 old_timestamp = bat->timestamp; + int old_energy_now = bat->energy_now; + /* reset values */ bat->present = 0; bat->status = BATTERY_UNKNOWN; bat->energy_now = 0; bat->energy_full = 0; bat->power_now = 0; + bat->timestamp = g_get_monotonic_time(); /* present */ g_file_get_contents(bat->path_present, &data, &datalen, &error);

@@ -329,9 +344,17 @@ g_free(data);

/* power now */ g_file_get_contents(bat->path_power_now, &data, &datalen, &error); - RETURN_ON_ERROR(error); - bat->power_now = atoi(data); - g_free(data); + if (g_error_matches(error, G_FILE_ERROR, G_FILE_ERROR_NODEV)) { + /* some hardware does not support reading current power consumption */ + g_error_free(error); + bat->power_now = estimate_power_usage(bat, old_energy_now, old_timestamp); + } else if(error) { + g_error_free(error); + return FALSE; + } else { + bat->power_now = atoi(data); + g_free(data); + } return TRUE; }