freebsd-ports/x11/mate-applets/files/patch-battstat_acpi-freebsd.c
Koop Mast a236e2d0bf Say hello to Mate 1.6.
Mate is a lite desktop forked from gnome2.

Most of the work is done by Jeremy Messenger (mezz@). The only thing I did
was update a few ports to later 1.6 release and attempting to keep up with
ports infra changes. Resulting bugs are all mine.

Mate is a sort of replacement for Gnome 2. So people wanting to keep a
Gnome 2 like desktop should switch. Gnome 2 will be replaced by Gnome 3
in the near future. This switch will be announce with a transition time
so people have more time to switch if they haven't already.

This release was made possible by everyone that send friendly pokes to
keep mate on my mind.

Approved by:	portmgr (bapt)
2013-11-23 11:39:07 +00:00

152 lines
3.6 KiB
C

--- battstat/acpi-freebsd.c.orig Sun Jul 3 16:41:26 2005
+++ battstat/acpi-freebsd.c Sun Jul 3 16:49:55 2005
@@ -31,9 +31,13 @@
#include <stdio.h>
#include <sys/types.h>
+#include <sys/socket.h>
#include <sys/sysctl.h>
+#include <sys/un.h>
#include <sys/ioctl.h>
+#if defined(__i386__)
#include <machine/apm_bios.h>
+#endif
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
@@ -92,16 +96,36 @@ gboolean
acpi_freebsd_init(struct acpi_info * acpiinfo)
{
int acpi_fd;
+ int event_fd;
g_assert(acpiinfo);
- acpi_fd = open(ACPIDEV, O_RDONLY);
- if (acpi_fd >= 0) {
- acpiinfo->acpifd = acpi_fd;
+ if (acpiinfo->acpifd == -1) {
+ acpi_fd = open(ACPIDEV, O_RDONLY);
+ if (acpi_fd >= 0) {
+ acpiinfo->acpifd = acpi_fd;
+ }
+ else {
+ acpiinfo->acpifd = -1;
+ return FALSE;
+ }
}
- else {
- acpiinfo->acpifd = -1;
- return FALSE;
+
+ event_fd = socket(PF_UNIX, SOCK_STREAM, 0);
+ if (event_fd >= 0) {
+ struct sockaddr_un addr;
+ addr.sun_family = AF_UNIX;
+ strcpy(addr.sun_path, "/var/run/devd.pipe");
+ if (connect(event_fd, (struct sockaddr *) &addr, sizeof(addr)) == 0) {
+ acpiinfo->event_fd = event_fd;
+ acpiinfo->event_inited = TRUE;
+ acpiinfo->channel = g_io_channel_unix_new(event_fd);
+ }
+ else {
+ close(event_fd);
+ acpiinfo->event_fd = -1;
+ acpiinfo->event_inited = FALSE;
+ }
}
update_battery_info(acpiinfo);
@@ -110,6 +134,65 @@ acpi_freebsd_init(struct acpi_info * acp
return TRUE;
}
+#define ACPI_EVENT_IGNORE 0
+#define ACPI_EVENT_AC 1
+#define ACPI_EVENT_BATTERY_INFO 2
+
+static int parse_acpi_event(GString *buffer)
+{
+ if (strstr(buffer->str, "system=ACPI")) {
+ if (strstr(buffer->str, "subsystem=ACAD"))
+ return ACPI_EVENT_AC;
+ if (strstr(buffer->str, "subsystem=CMBAT"))
+ return ACPI_EVENT_BATTERY_INFO;
+ }
+
+ return ACPI_EVENT_IGNORE;
+}
+
+void acpi_freebsd_update(struct acpi_info *acpiinfo)
+{
+ /* XXX This is needed for systems where devd does not have permissions
+ * to allow for event-driven updates.
+ */
+ update_ac_info(acpiinfo);
+ update_battery_info(acpiinfo);
+}
+
+gboolean acpi_process_event(struct acpi_info *acpiinfo, gboolean *read_error)
+{
+ gsize i;
+ int evt;
+ gboolean result = FALSE;
+ GString *buffer;
+ GIOStatus stat;
+ buffer = g_string_new(NULL);
+
+ *read_error = FALSE;
+ stat = g_io_channel_read_line_string(acpiinfo->channel, buffer, &i, NULL);
+
+ if (stat == G_IO_STATUS_ERROR || stat == G_IO_STATUS_EOF) {
+ *read_error = TRUE;
+ g_string_free(buffer, TRUE);
+ return FALSE;
+ }
+
+ evt = parse_acpi_event(buffer);
+ switch (evt) {
+ case ACPI_EVENT_AC:
+ update_ac_info(acpiinfo);
+ result = TRUE;
+ break;
+ case ACPI_EVENT_BATTERY_INFO:
+ update_battery_info(acpiinfo);
+ result = TRUE;
+ break;
+ }
+
+ g_string_free(buffer, TRUE);
+ return result;
+}
+
void
acpi_freebsd_cleanup(struct acpi_info * acpiinfo)
{
@@ -119,21 +202,12 @@ acpi_freebsd_cleanup(struct acpi_info *
close(acpiinfo->acpifd);
acpiinfo->acpifd = -1;
}
-}
-/* XXX This is a hack since user-land applications can't get ACPI events yet.
- * Devd provides this (or supposedly provides this), but you need to be
- * root to access devd.
- */
-gboolean
-acpi_process_event(struct acpi_info * acpiinfo)
-{
- g_assert(acpiinfo);
-
- update_ac_info(acpiinfo);
- update_battery_info(acpiinfo);
-
- return TRUE;
+ if (acpiinfo->event_fd >= 0) {
+ g_io_channel_unref(acpiinfo->channel);
+ close(acpiinfo->event_fd);
+ acpiinfo->event_fd = -1;
+ }
}
gboolean