tags #524997 patch
thanks

The project of my variant package in attache.

It supports apm (old variant) and ACPI (new variant).
It contains a few changes in debian/rules and debian/control.

So package has been uploaded to mentros:
http://mentors.debian.net/debian/pool/main/x/xbattbar/

On 15:51 Tue 21 Apr     , Dmitry E. Oboukhov wrote:
Tsbdo> Package: xbattbar
Tsbdo> Severity: wishlist

Tsbdo> Now xbattbar does not support majority of modern hardware. Upstream
Tsbdo> had been neglect since 2001.

Tsbdo> I have rewritten part of src (I added a few options into command line
Tsbdo> and split the binary to two binaries: xbattbar and xbattbar-check-apm).
Tsbdo> Following i think to write a few additional check scripts (ACPI) for
Tsbdo> my patched source and upload the results into Debian.

Tsbdo> But I am not maintainer xbattbar. Could You give me rights to
Tsbdo> upload (add me to 'uploaders' group or orphan the package)?

Tsbdo> thanks
--
... mpd is off

. ''`.                               Dmitry E. Oboukhov
: :’  :   email: un...@debian.org jabber://un...@uvw.ru
`. `~’              GPGKey: 1024D / F8E26537 2006-11-21
  `- 1B23 D4F8 8EC0 D902 0555  E438 AB8C 00CF F8E2 6537
diff -Nru xbattbar-1.4.2/Imakefile xbattbar-1.4.3/Imakefile
--- xbattbar-1.4.2/Imakefile    2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/Imakefile    1970-01-01 03:00:00.000000000 +0300
@@ -1,28 +0,0 @@
-XCOMM $Id: Imakefile,v 1.6.2.1 2001/02/02 05:25:28 suguru Exp $
-XCOMM
-XCOMM Copyright (c) 1998-2001 Suguru Yamaguchi <sug...@wide.ad.jp>
-XCOMM 
-XCOMM This program is free software; you can redistribute it and/or modify it
-XCOMM under the terms of the GNU General Public License as published
-XCOMM by the Free Software Foundation; either version 2 of the License, or (at
-XCOMM your option) any later version.
-XCOMM 
-XCOMM This program is distributed in the hope that it will be useful, but
-XCOMM WITHOUT ANY WARRANTY; without even the implied warranty of
-XCOMM MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
-XCOMM General Public License for more details.
-XCOMM 
-XCOMM You should have received a copy of the GNU General Public
-XCOMM License along with this program; if not, write to the Free Software
-XCOMM Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-XCOMM 
-
-MANDIR = /usr/share/man/man1
-
-LOCAL_LIBRARIES = $(XLIB)
-
-SRCS = xbattbar.c
-OBJS = xbattbar.o
-TARGET = xbattbar
-
-ComplexProgramTarget($(TARGET))
diff -Nru xbattbar-1.4.2/Makefile xbattbar-1.4.3/Makefile
--- xbattbar-1.4.2/Makefile     1970-01-01 03:00:00.000000000 +0300
+++ xbattbar-1.4.3/Makefile     2009-04-23 11:09:31.000000000 +0400
@@ -0,0 +1,40 @@
+OS_TYPE                ?=      linux
+PROJECT                =       xbattbar
+DESTDIR                ?=      /
+
+TARGET         =       xbattbar
+APM_CHECK      =       xbattbar-check-apm
+
+all: $(TARGET) $(APM_CHECK)
+
+$(TARGET): obj/xbattbar.o
+       gcc -o $@ $< -lX11
+
+obj/xbattbar.o: xbattbar.c obj/stamp
+       gcc -MMD -o $@ -c $<
+
+$(APM_CHECK): obj/xbattbar-check-apm.o
+       gcc -o $@ $<
+
+obj/xbattbar-check-apm.o: xbattbar-check-apm.c obj/stamp
+       gcc -MMD -D$(OS_TYPE) -o $@ -c $<
+
+obj/stamp:
+       mkdir obj
+       touch $@
+
+clean:
+       rm -fr obj
+       rm -f $(TARGET) $(APM_CHECK)
+
+
+install: $(TARGET) $(APM_CHECK)
+       install -d -m 0755 $(DESTDIR)/usr/lib/$(PROJECT)
+       install -d -m 0755 $(DESTDIR)/usr/bin
+       install -d -m 0755 $(DESTDIR)/usr/share/man/man1
+       install -m 0755 $(APM_CHECK) $(DESTDIR)/usr/lib/$(PROJECT)/
+       install -m 0755 xbattbar-check-acpi $(DESTDIR)/usr/lib/$(PROJECT)/
+       install -m 0755 $(TARGET) $(DESTDIR)/usr/bin/
+       install -m 0644 xbattbar.man $(DESTDIR)/usr/share/man/man1/$(PROJECT).1 
+
+include $(wildcard obj/*.d) 
diff -Nru xbattbar-1.4.2/debian/changelog xbattbar-1.4.3/debian/changelog
--- xbattbar-1.4.2/debian/changelog     2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/debian/changelog     2009-04-23 16:34:54.000000000 +0400
@@ -1,3 +1,16 @@
+xbattbar (1.4.3-1) unstable; urgency=low
+
+  * New uploader, closes: #524997;
+  * Upstream version has been incremented.
+  * Upstream make system was rewritten.
+  * Added ACPI support for xbattbar.
+  * Fixed description, closes: #517682.
+  * Unnecessary dependencies have been dropped.
+  * Manpage has been updated.
+  * Standards-Version has been bumped to 3.8.0.
+
+ -- Dmitry E. Oboukhov <un...@debian.org>  Thu, 23 Apr 2009 11:05:20 +0400
+
 xbattbar (1.4.2-5.1) unstable; urgency=low
 
   * Non-maintainer upload.
diff -Nru xbattbar-1.4.2/debian/control xbattbar-1.4.3/debian/control
--- xbattbar-1.4.2/debian/control       2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/debian/control       2009-04-23 16:34:54.000000000 +0400
@@ -2,12 +2,14 @@
 Section: x11
 Priority: optional
 Maintainer: Davide Truffa <dav...@catoblepa.org>
-Build-Depends: debhelper (>> 5.0.0), xutils-dev, libx11-dev, libxext-dev
-Standards-Version: 3.7.2
+Uploaders:  Dmitry E. Oboukhov <un...@debian.org>
+Build-Depends: debhelper (>> 5.0.0), libx11-dev
+Standards-Version: 3.8.0
 
 Package: xbattbar
 Architecture: any
 Depends: ${shlibs:Depends}
+Recommends: acpi
 Description: Display battery status in X11
  Xbattbar displays the current (laptop) battery status in the X window
  environment. Battery status is obtained through the APM interface.
@@ -19,4 +21,4 @@
  diagnosis window comes up in the center of your display showing the
  current AC line status and battery level.
  .
- If you use ACPI take a look at xbattbar-acpi. 
+ This package supports ACPI and APM checks for battery status.
diff -Nru xbattbar-1.4.2/debian/copyright xbattbar-1.4.3/debian/copyright
--- xbattbar-1.4.2/debian/copyright     2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/debian/copyright     2009-04-23 16:34:54.000000000 +0400
@@ -4,10 +4,12 @@
 The current Debian maintainer is Davide truffa <dav...@catoblepa.org>
 
 It was downloaded from http://iplab.aist-nara.ac.jp/member/suguru/xbattbar.html
+It was modified by Dmitry E. Oboukhov <un...@debian.org>
 
 Upstream Author: Suguru Yamaguchi <sug...@wide.ad.jp>
 
-Copyright: (c) 1998-2001 Suguru Yamaguchi
+ Copyright (c) 1998-2001 Suguru Yamaguchi
+ Copyright (c) Dmitry E. Oboukhov <un...@debian.org>
 
 
 License:
diff -Nru xbattbar-1.4.2/debian/rules xbattbar-1.4.3/debian/rules
--- xbattbar-1.4.2/debian/rules 2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/debian/rules 2009-04-23 16:34:54.000000000 +0400
@@ -1,16 +1,9 @@
 #!/usr/bin/make -f
 #export DH_VERBOSE=1
 
-configure: configure-stamp
-
-configure-stamp:
-       dh_testdir
-       xmkmf -a
-       touch configure-stamp
-
 build: build-stamp
 
-build-stamp: configure-stamp 
+build-stamp:
        dh_testdir
        $(MAKE)
        touch build-stamp
@@ -19,7 +12,7 @@
        dh_testdir
        dh_testroot
        rm -f build-stamp configure-stamp
-       $(MAKE) distclean || true
+       $(MAKE) clean
        dh_clean
 
 install: build
@@ -27,17 +20,15 @@
        dh_testroot
        dh_clean -k
        dh_installdirs
-       $(MAKE) install DESTDIR=$(CURDIR)/debian/xbattbar
-       install -d -o0 -g0 $(CURDIR)/debian/xbattbar/usr/share/man/man1/
-       install -o0 -g0 -m644 xbattbar.man 
$(CURDIR)/debian/xbattbar/usr/share/man/man1/xbattbar.1x
+       $(MAKE) install OS_TYPE=linux DESTDIR=$(CURDIR)/debian/xbattbar
 
 binary-indep: build install
 
 binary-arch: build install
        dh_testdir
        dh_testroot
-       dh_installdocs README
        dh_installmenu
+       dh_installdocs
        dh_installchangelogs 
        dh_link
        dh_strip
diff -Nru xbattbar-1.4.2/xbattbar-check-acpi xbattbar-1.4.3/xbattbar-check-acpi
--- xbattbar-1.4.2/xbattbar-check-acpi  1970-01-01 03:00:00.000000000 +0300
+++ xbattbar-1.4.3/xbattbar-check-acpi  2009-04-23 12:15:08.000000000 +0400
@@ -0,0 +1,44 @@
+#!/usr/bin/perl
+#  *************************************************************************
+#  *                                                                       *
+#  * Copyright (C) 2009 Dmitry E. Oboukhov <un...@debian.org>              *
+#  *                                                                       *
+#  * This program is free software: you can redistribute it and/or modify  *
+#  * it under the terms of the GNU General Public License as published by  *
+#  * the Free Software Foundation, either version 3 of the License, or     *
+#  * (at your option) any later version.                                   *
+#  *                                                                       *
+#  * This program is distributed in the hope that it will be useful,       *
+#  * but WITHOUT ANY WARRANTY; without even the implied warranty of        *
+#  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
+#  * GNU General Public License for more details.                          *
+#  *                                                                       *
+#  * You should have received a copy of the GNU General Public License     *
+#  * along with this program.  If not, see <http://www.gnu.org/licenses/>. *
+#  *                                                                       *
+#  *************************************************************************
+
+use warnings;
+use strict;
+
+my $acpi;
+
+die "Can not start acpi: $!\n" unless open $acpi, '-|', 'acpi', '-b', '-a';
+
+my @acpi = <$acpi>;
+
+my @battery =
+    grep { defined $_ and /^\d+$/ }
+    map { s/^.*\s+(\d+)%.*/$1/; $_ }
+    grep /Battery\s+\d+:/, @acpi;
+
+die "Can not get battery level\n" unless @battery;
+
+my $battery = 0;
+$battery += $_ for @battery;
+$battery /= @battery;
+
+my $ac = grep /Adapter.*on-line/, @acpi;
+
+printf "battery=%d\nac_line=%s\n", 
+    $battery, $ac?"on":"off";
diff -Nru xbattbar-1.4.2/xbattbar-check-apm.c 
xbattbar-1.4.3/xbattbar-check-apm.c
--- xbattbar-1.4.2/xbattbar-check-apm.c 1970-01-01 03:00:00.000000000 +0300
+++ xbattbar-1.4.3/xbattbar-check-apm.c 2009-04-23 15:59:50.000000000 +0400
@@ -0,0 +1,275 @@
+/*
+ * Copyright (c) 1998-2001 Suguru Yamaguchi <sug...@wide.ad.jp>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2 of the License, or (at
+ * your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * Modified 2009 by Dmitry E. Oboukhov <un...@debian.org>:
+ *   SRC has been split to two parts: bar and battery-check
+ *   This part contains APM battery-check part of xbattbar
+ */
+
+#include <stdio.h>
+#include <unistd.h>
+
+static int ac_line = -1;               /* AC line status */
+static int battery_level = -1;         /* battery level */
+
+void battery_check(void);
+
+int main(int argc, char **argv)
+{
+       battery_check();
+       if (battery_level == -1) {
+               fprintf(stderr, "Can not get battery level\n");
+               return 1;
+       }
+
+       printf("battery=%d\nac_line=%s\n", battery_level, ac_line?"on":"off");
+       return 0;
+}
+
+
+#ifdef __bsdi__
+
+#include <machine/apm.h>
+#include <machine/apmioctl.h>
+
+int first = 1;
+void battery_check(void)
+{
+  int fd;
+  struct apmreq ar ;
+
+  ar.func = APM_GET_POWER_STATUS ;
+  ar.dev = APM_DEV_ALL ;
+
+  if ((fd = open(_PATH_DEVAPM, O_RDONLY)) < 0) {
+    perror(_PATH_DEVAPM) ;
+    exit(1) ;
+  }
+  if (ioctl(fd, PIOCAPMREQ, &ar) < 0) {
+    fprintf(stderr, "xbattbar: PIOCAPMREQ: APM_GET_POWER_STATUS error 0x%x\n", 
ar.err);
+  }
+  close (fd);
+
+  if (first || ac_line != ((ar.bret >> 8) & 0xff)
+      || battery_level != (ar.cret&0xff)) {
+    first = 0;
+    ac_line = (ar.bret >> 8) & 0xff;
+    battery_level = ar.cret&0xff;
+  }
+}
+
+#endif /* __bsdi__ */
+
+#ifdef __FreeBSD__
+
+#include <machine/apm_bios.h>
+
+#define APMDEV21       "/dev/apm0"
+#define APMDEV22       "/dev/apm"
+
+#define        APM_STAT_UNKNOWN        255
+
+#define        APM_STAT_LINE_OFF       0
+#define        APM_STAT_LINE_ON        1
+
+#define        APM_STAT_BATT_HIGH      0
+#define        APM_STAT_BATT_LOW       1
+#define        APM_STAT_BATT_CRITICAL  2
+#define        APM_STAT_BATT_CHARGING  3
+
+int first = 1;
+void battery_check(void)
+{
+  int fd, r, p;
+  struct apm_info     info;
+
+  if ((fd = open(APMDEV21, O_RDWR)) == -1 &&
+      (fd = open(APMDEV22, O_RDWR)) == -1) {
+    fprintf(stderr, "xbattbar: cannot open apm device\n");
+    exit(1);
+  }
+  if (ioctl(fd, APMIO_GETINFO, &info) == -1) {
+    fprintf(stderr, "xbattbar: ioctl APMIO_GETINFO failed\n");
+    exit(1);
+  }
+  close (fd);
+
+  /* get current status */
+  if (info.ai_batt_life == APM_STAT_UNKNOWN) {
+    switch (info.ai_batt_stat) {
+    case APM_STAT_BATT_HIGH:
+      r = 100;
+      break;
+    case APM_STAT_BATT_LOW:
+      r = 40;
+      break;
+    case APM_STAT_BATT_CRITICAL:
+      r = 10;
+      break;
+    default:        /* expected to be APM_STAT_UNKNOWN */
+      r = 100;
+    }
+  } else if (info.ai_batt_life > 100) {
+    /* some APM BIOSes return values slightly > 100 */
+    r = 100;
+  } else {
+    r = info.ai_batt_life;
+  }
+
+  /* get AC-line status */
+  if (info.ai_acline == APM_STAT_LINE_ON) {
+    p = APM_STAT_LINE_ON;
+  } else {
+    p = APM_STAT_LINE_OFF;
+  }
+
+  if (first || ac_line != p || battery_level != r) {
+    first = 0;
+    ac_line = p;
+    battery_level = r;
+  }
+}
+
+#endif /* __FreeBSD__ */
+
+#ifdef __NetBSD__
+
+#include <machine/apmvar.h>
+
+#define _PATH_APM_SOCKET       "/var/run/apmdev"
+#define _PATH_APM_CTLDEV       "/dev/apmctl"
+#define _PATH_APM_NORMAL       "/dev/apm"
+
+int first = 1;
+void battery_check(void)
+{
+       int fd, r, p;
+       struct apm_power_info info;
+
+       if ((fd = open(_PATH_APM_NORMAL, O_RDONLY)) == -1) {
+               fprintf(stderr, "xbattbar: cannot open apm device\n");
+               exit(1);
+       }
+
+       if (ioctl(fd, APM_IOC_GETPOWER, &info) != 0) {
+               fprintf(stderr, "xbattbar: ioctl APM_IOC_GETPOWER failed\n");
+               exit(1);
+       }
+
+       close(fd);
+
+       /* get current remoain */
+       if (info.battery_life > 100) {
+               /* some APM BIOSes return values slightly > 100 */
+               r = 100;
+       } else {
+               r = info.battery_life;
+       }
+
+       /* get AC-line status */
+       if (info.ac_state == APM_AC_ON) {
+               p = APM_AC_ON;
+       } else {
+               p = APM_AC_OFF;
+       }
+
+       if (first || ac_line != p || battery_level != r) {
+               first = 0;
+               ac_line = p;
+               battery_level = r;
+       }
+}
+
+#endif /* __NetBSD__ */
+
+
+#ifdef linux
+
+#include <errno.h>
+#include <linux/apm_bios.h>
+
+#define APM_PROC       "/proc/apm"
+
+#define        APM_STAT_LINE_OFF       0
+#define        APM_STAT_LINE_ON        1
+
+typedef struct apm_info {
+   const char driver_version[10];
+   int        apm_version_major;
+   int        apm_version_minor;
+   int        apm_flags;
+   int        ac_line_status;
+   int        battery_status;
+   int        battery_flags;
+   int        battery_percentage;
+   int        battery_time;
+   int        using_minutes;
+} apm_info;
+
+
+int first = 1;
+void battery_check(void)
+{
+  int r,p;
+  FILE *pt;
+  struct apm_info i;
+  char buf[100];
+
+  /* get current status */
+  errno = 0;
+  if ( (pt = fopen( APM_PROC, "r" )) == NULL) {
+    fprintf(stderr, "xbattbar: Can't read proc info: %s\n", strerror(errno));
+    _exit(1);
+  }
+
+  fgets( buf, sizeof( buf ) - 1, pt );
+  buf[ sizeof( buf ) - 1 ] = '\0';
+  sscanf( buf, "%s %d.%d %x %x %x %x %d%% %d %d\n",
+         &i.driver_version,
+         &i.apm_version_major,
+         &i.apm_version_minor,
+         &i.apm_flags,
+         &i.ac_line_status,
+         &i.battery_status,
+         &i.battery_flags,
+         &i.battery_percentage,
+         &i.battery_time,
+         &i.using_minutes );
+
+  fclose (pt);
+
+   /* some APM BIOSes return values slightly > 100 */
+   if ( (r = i.battery_percentage) > 100 ){
+     r = 100;
+   }
+
+   /* get AC-line status */
+   if ( i.ac_line_status == APM_STAT_LINE_ON) {
+     p = APM_STAT_LINE_ON;
+   } else {
+     p = APM_STAT_LINE_OFF;
+   }
+
+  if (first || ac_line != p || battery_level != r) {
+    first = 0;
+    ac_line = p;
+    battery_level = r;
+  }
+}
+
+#endif /* linux */
+
diff -Nru xbattbar-1.4.2/xbattbar.c xbattbar-1.4.3/xbattbar.c
--- xbattbar-1.4.2/xbattbar.c   2001-02-02 08:25:29.000000000 +0300
+++ xbattbar-1.4.3/xbattbar.c   2009-04-23 16:29:54.000000000 +0400
@@ -11,28 +11,36 @@
  * under the terms of the GNU General Public License as published
  * by the Free Software Foundation; either version 2 of the License, or (at
  * your option) any later version.
- * 
+ *
  * This program is distributed in the hope that it will be useful, but
  * WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  * General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public
  * License along with this program; if not, write to the Free Software
  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
- * 
+ *
+ * Modified 2009 by Dmitry E. Oboukhov <un...@debian.org>:
+ *   SRC has been split to two parts: bar and battery-check
+ *   This part contains bar part of xbattbar
  */
 
 static char *ReleaseVersion="1.4.2";
 
 #include <sys/types.h>
 #include <sys/time.h>
+#include <sys/wait.h>
 #include <signal.h>
 #include <stdio.h>
 #include <unistd.h>
 #include <sys/file.h>
 #include <sys/ioctl.h>
 #include <X11/Xlib.h>
+#include <string.h>
+#include <unistd.h>
+#include <errno.h>
+#include <stdlib.h>
 
 #define PollingInterval 10     /* APM polling interval in sec */
 #define BI_THICKNESS    3      /* battery indicator thickness in pixels */
@@ -67,6 +75,9 @@
 char *OFFIN_C  = "blue";
 char *OFFOUT_C = "red";
 
+char *EXTERNAL_CHECK = "/usr/lib/xbattbar/xbattbar-check-apm";
+char *EXTERNAL_CHECK_ACPI = "/usr/lib/xbattbar/xbattbar-check-acpi";
+
 int alwaysontop = False;
 
 struct itimerval IntervalTimer;     /* APM polling interval timer */
@@ -107,28 +118,32 @@
  */
 void about_this_program()
 {
-  fprintf(stderr, 
+  fprintf(stderr,
          "This is xbattbar version %s, "
-         "copyright (c)1998-2001 Suguru Yamaguchi\n",
+         " Copyright (c) 1998-2001 Suguru Yamaguchi\n"
+         "  modified 2009 by Dmitry E. Oboukhov <un...@debian.org>\n",
          ReleaseVersion);
 }
 
 void usage(char **argv)
 {
   fprintf(stderr,
-    "\n"         
+    "\n"
     "usage:\t%s [-a] [-h|v] [-p sec] [-t thickness]\n"
     "\t\t[-I color] [-O color] [-i color] [-o color]\n"
     "\t\t[ top | bottom | left | right ]\n"
-    "-a:     always on top.\n"
-    "-v, -h: show this message.\n"
-    "-t:     bar (indicator) thickness. [def: 3 pixels]\n"
-    "-p:     polling interval. [def: 10 sec.]\n"
-    "-I, -O: bar colors in AC on-line. [def: \"green\" & \"olive drab\"]\n"
-    "-i, -o: bar colors in AC off-line. [def: \"blue\" and \"red\"]\n"
-    "top, bottom, left, right: bar localtion. [def: \"bottom\"]\n",
-         argv[0]);
-  exit(0);
+    "-a:         always on top.\n"
+    "-v, -h:     show this message.\n"
+    "-t:         bar (indicator) thickness. [def: 3 pixels]\n"
+    "-p:         polling interval. [def: 10 sec.]\n"
+    "-I, -O:     bar colors in AC on-line. [def: \"green\" & \"olive drab\"]\n"
+    "-i, -o:     bar colors in AC off-line. [def: \"blue\" and \"red\"]\n"
+    "top, bottom, left, right: bar localtion. [def: \"bottom\"]\n"
+    "\n"
+    "-c:         use ACPI checker for getting battery status\n"
+    "-s script:  use external script for getting battery status\n",
+    argv[0]);
+  _exit(0);
 }
 
 /*
@@ -160,13 +175,13 @@
 
   if((disp = XOpenDisplay(NULL)) == NULL) {
       fprintf(stderr, "xbattbar: can't open display.\n");
-      exit(1);
+      _exit(1);
   }
 
   if(XGetGeometry(disp, DefaultRootWindow(disp), &root, &x, &y,
                  &width, &height, &border, &depth) == 0) {
     fprintf(stderr, "xbattbar: can't get window geometry\n");
-    exit(1);
+    _exit(1);
   }
 
   if (!AllocColor(ONIN_C,&onin) ||
@@ -174,7 +189,7 @@
        !AllocColor(OFFIN_C,&offin) ||
        !AllocColor(ONOUT_C,&onout)) {
     fprintf(stderr, "xbattbar: can't allocate color resources\n");
-    exit(1);
+    _exit(1);
   }
 
   switch (bi_direction) {
@@ -223,8 +238,16 @@
   int ch;
 
   about_this_program();
-  while ((ch = getopt(argc, argv, "at:f:hI:i:O:o:p:v")) != -1)
+  while ((ch = getopt(argc, argv, "at:f:hI:i:O:o:p:vs:c")) != -1)
     switch (ch) {
+    case 'c':
+      EXTERNAL_CHECK = EXTERNAL_CHECK_ACPI;
+      break;
+
+    case 's':
+      EXTERNAL_CHECK = optarg;
+      break;
+
     case 'a':
       alwaysontop = True;
       break;
@@ -273,14 +296,11 @@
   /*
    * set APM polling interval timer
    */
-  IntervalTimer.it_interval.tv_sec = (long)bi_interval;
-  IntervalTimer.it_interval.tv_usec = (long)0;
-  IntervalTimer.it_value.tv_sec = (long)1;
-  IntervalTimer.it_value.tv_usec = (long)0;
-  if ( setitimer(ITIMER_REAL, &IntervalTimer, NULL) != 0 ) {
+  if (!bi_interval) {
     fprintf(stderr,"xbattbar: can't set interval timer\n");
-    exit(1);
+    _exit(1);
   }
+  alarm(bi_interval);
 
   /*
    * X Window main loop
@@ -313,7 +333,7 @@
 
     default:
       /* for debugging */
-      fprintf(stderr, 
+      fprintf(stderr,
              "xbattbar: unknown event (%d) captured\n",
              theEvent.type);
     }
@@ -418,7 +438,7 @@
 
 
 /*
- * estimating time for battery remaining / charging 
+ * estimating time for battery remaining / charging
  */
 
 #define CriticalLevel  5
@@ -460,253 +480,136 @@
   battery_base = battery_level;
 }
 
+#define TEMP_BUFFER_SIZE 4096
 
-
-#ifdef __bsdi__
-
-#include <machine/apm.h>
-#include <machine/apmioctl.h>
-
-int first = 1;
-void battery_check(void)
+int read_pipe(int pipe, char *buffer)
 {
-  int fd;
-  struct apmreq ar ;
-
-  ++elapsed_time;
-
-  ar.func = APM_GET_POWER_STATUS ;
-  ar.dev = APM_DEV_ALL ;
-
-  if ((fd = open(_PATH_DEVAPM, O_RDONLY)) < 0) {
-    perror(_PATH_DEVAPM) ;
-    exit(1) ;
-  }
-  if (ioctl(fd, PIOCAPMREQ, &ar) < 0) {
-    fprintf(stderr, "xbattbar: PIOCAPMREQ: APM_GET_POWER_STATUS error 0x%x\n", 
ar.err);
-  }
-  close (fd);
-
-  if (first || ac_line != ((ar.bret >> 8) & 0xff)
-      || battery_level != (ar.cret&0xff)) {
-    first = 0;
-    ac_line = (ar.bret >> 8) & 0xff;
-    battery_level = ar.cret&0xff;
-    redraw();
-  }
-  signal(SIGALRM, (void *)(battery_check));
-}
-
-#endif /* __bsdi__ */
-
-#ifdef __FreeBSD__
-
-#include <machine/apm_bios.h>
-
-#define APMDEV21       "/dev/apm0"
-#define APMDEV22       "/dev/apm"
-
-#define        APM_STAT_UNKNOWN        255
-
-#define        APM_STAT_LINE_OFF       0
-#define        APM_STAT_LINE_ON        1
-
-#define        APM_STAT_BATT_HIGH      0
-#define        APM_STAT_BATT_LOW       1
-#define        APM_STAT_BATT_CRITICAL  2
-#define        APM_STAT_BATT_CHARGING  3
-
-int first = 1;
-void battery_check(void)
-{
-  int fd, r, p;
-  struct apm_info     info;
-
-  if ((fd = open(APMDEV21, O_RDWR)) == -1 &&
-      (fd = open(APMDEV22, O_RDWR)) == -1) {
-    fprintf(stderr, "xbattbar: cannot open apm device\n");
-    exit(1);
-  }
-  if (ioctl(fd, APMIO_GETINFO, &info) == -1) {
-    fprintf(stderr, "xbattbar: ioctl APMIO_GETINFO failed\n");
-    exit(1);
-  }
-  close (fd);
-
-  ++elapsed_time;
-
-  /* get current status */
-  if (info.ai_batt_life == APM_STAT_UNKNOWN) {
-    switch (info.ai_batt_stat) {
-    case APM_STAT_BATT_HIGH:
-      r = 100;
-      break;
-    case APM_STAT_BATT_LOW:
-      r = 40;
-      break;
-    case APM_STAT_BATT_CRITICAL:
-      r = 10;
-      break;
-    default:        /* expected to be APM_STAT_UNKNOWN */
-      r = 100;
-    }
-  } else if (info.ai_batt_life > 100) {
-    /* some APM BIOSes return values slightly > 100 */
-    r = 100;
-  } else {
-    r = info.ai_batt_life;
-  }
+       int rd = read(pipe, buffer, TEMP_BUFFER_SIZE - 1);
+       if (rd == -1) {
+               perror("read pipe");
+               return 0;
+       }
+       buffer[rd] = 0;
+       return rd;
+}
+
+#define BATTERY_STRING         "battery="
+#define AC_LINE_STRING         "ac_line="
+void print_script_error(void)
+{
+       fprintf(stderr, "\nExternal script must print two strings:\n"
+               "\t" BATTERY_STRING "value between 0 and 100\n"
+               "\t" AC_LINE_STRING "on|off\n"
+               "example 1:\n"
+               "\t" BATTERY_STRING "25\n"
+               "\t" AC_LINE_STRING "on\n"
+               "example 2:\n"
+               "\t" BATTERY_STRING "75\n"
+               "\t" AC_LINE_STRING "off\n"
+       );
 
-  /* get AC-line status */
-  if (info.ai_acline == APM_STAT_LINE_ON) {
-    p = APM_STAT_LINE_ON;
-  } else {
-    p = APM_STAT_LINE_OFF;
-  }
-
-  if (first || ac_line != p || battery_level != r) {
-    first = 0;
-    ac_line = p;
-    battery_level = r;
-    redraw();
-  }
-  signal(SIGALRM, (void *)(battery_check));
 }
 
-#endif /* __FreeBSD__ */
-
-#ifdef __NetBSD__
-
-#include <machine/apmvar.h>
-
-#define _PATH_APM_SOCKET       "/var/run/apmdev"
-#define _PATH_APM_CTLDEV       "/dev/apmctl"
-#define _PATH_APM_NORMAL       "/dev/apm"
-
-int first = 1;
 void battery_check(void)
 {
-       int fd, r, p;
-       struct apm_power_info info;
-
-       if ((fd = open(_PATH_APM_NORMAL, O_RDONLY)) == -1) {
-               fprintf(stderr, "xbattbar: cannot open apm device\n");
-               exit(1);
-       }
-
-       if (ioctl(fd, APM_IOC_GETPOWER, &info) != 0) {
-               fprintf(stderr, "xbattbar: ioctl APM_IOC_GETPOWER failed\n");
-               exit(1);
-       }
-
-       close(fd);
-
-       ++elapsed_time;
-
-       /* get current remoain */
-       if (info.battery_life > 100) {
-               /* some APM BIOSes return values slightly > 100 */
-               r = 100;
-       } else {
-               r = info.battery_life;
-       }
-
-       /* get AC-line status */
-       if (info.ac_state == APM_AC_ON) {
-               p = APM_AC_ON;
-       } else {
-               p = APM_AC_OFF;
-       }
-
-       if (first || ac_line != p || battery_level != r) {
-               first = 0;
-               ac_line = p;
-               battery_level = r;
-               redraw();
-       }
-}
-
-#endif /* __NetBSD__ */
-
-
-#ifdef linux
-
-#include <errno.h>
-#include <linux/apm_bios.h>
+       int p[2], pid;
+       char buffer[TEMP_BUFFER_SIZE];
 
-#define APM_PROC       "/proc/apm"
-
-#define        APM_STAT_LINE_OFF       0
-#define        APM_STAT_LINE_ON        1
-
-typedef struct apm_info {
-   const char driver_version[10];
-   int        apm_version_major;
-   int        apm_version_minor;
-   int        apm_flags;
-   int        ac_line_status;
-   int        battery_status;
-   int        battery_flags;
-   int        battery_percentage;
-   int        battery_time;
-   int        using_minutes;
-} apm_info;
-
-
-int first = 1;
-void battery_check(void)
-{
-  int r,p;
-  FILE *pt;
-  struct apm_info i;
-  char buf[100];
-
-  /* get current status */
-  errno = 0;
-  if ( (pt = fopen( APM_PROC, "r" )) == NULL) {
-    fprintf(stderr, "xbattbar: Can't read proc info: %s\n", strerror(errno));
-    signal(SIGALRM, (void *)(battery_check));
-    exit(1);
-  }
-
-  fgets( buf, sizeof( buf ) - 1, pt );
-  buf[ sizeof( buf ) - 1 ] = '\0';
-  sscanf( buf, "%s %d.%d %x %x %x %x %d%% %d %d\n",
-         &i.driver_version,
-         &i.apm_version_major,
-         &i.apm_version_minor,
-         &i.apm_flags,
-         &i.ac_line_status,
-         &i.battery_status,
-         &i.battery_flags,
-         &i.battery_percentage,
-         &i.battery_time,
-         &i.using_minutes );
-
-  fclose (pt);
-
-  ++elapsed_time;
-
-   /* some APM BIOSes return values slightly > 100 */
-   if ( (r = i.battery_percentage) > 100 ){
-     r = 100;
-   }
-
-   /* get AC-line status */
-   if ( i.ac_line_status == APM_STAT_LINE_ON) {
-     p = APM_STAT_LINE_ON;
-   } else {
-     p = APM_STAT_LINE_OFF;
-   }
-
-  if (first || ac_line != p || battery_level != r) {
-    first = 0;
-    ac_line = p;
-    battery_level = r;
-    redraw();
-  }
-  signal(SIGALRM, (void *)(battery_check));
+       if (pipe(p) != 0) {
+               perror("error create pipe");
+               goto exit_check;
+       }
+
+       pid = fork();
+
+       if (pid == -1) {
+               perror("fork error");
+               close(p[0]);
+               close(p[1]);
+               goto exit_check;
+       }
+
+       if (pid) { /* parent */
+               int len, status;
+               close(p[1]);
+               char *str, *end;
+
+               pid = waitpid(pid, &status, 0);
+               if (pid == -1) {
+                       perror("waitpid");
+                       close(p[0]);
+                       goto exit_check;
+               }
+
+               if (status != 0) {
+                       fprintf(stderr,
+                               "child process (%s) has returned "
+                               "non-zero code: %d\n",
+                               EXTERNAL_CHECK, WEXITSTATUS(status));
+                       len = read_pipe(p[0], buffer);
+                       if (len > 0)
+                               printf("%s\n", buffer);
+                       close(p[0]);
+                       goto exit_check;
+               }
+
+               len = read_pipe(p[0], buffer);
+               close(p[0]);
+               if (!len) {
+                       print_script_error();
+                       goto exit_check;
+               }
+
+               str = strstr(buffer, BATTERY_STRING);
+               if (!str) {
+                       print_script_error();
+                       goto exit_check;
+               }
+
+               str += sizeof(BATTERY_STRING) - 1;
+               if (!*str) {
+                       print_script_error();
+                       goto exit_check;
+               }
+
+               status = strtol(str, &end, 10);
+               if ((*end != '\n' && *end != '.' &&
+                       *end != '\0' &&
+                       *end != ' ' && *end != '%') || end == str) {
+                       print_script_error();
+                       goto exit_check;
+               }
+               battery_level = status;
+               if (battery_level > 100)
+                       fprintf(stderr, "Incorrect battery level "
+                       " has been received: %d%%\n", battery_level);
+
+               if (strstr(buffer, AC_LINE_STRING "on"))
+                       ac_line = 1;
+               else
+                       ac_line = 0;
+
+/*                 printf("Received battery level: %d%%, ac_line: %s\n", */
+/*                         battery_level, ac_line?"on":"off"); */
+
+       } else { /* child */
+               char *argv[] = { EXTERNAL_CHECK, NULL };
+               close(p[0]);
+               if (dup2(p[1], fileno(stdout)) == -1) {
+                       perror("dup2 error");
+                       _exit(errno);
+               }
+               execvp(EXTERNAL_CHECK, argv);
+               fprintf(stderr, "Exec %s error: %s\n",
+                       EXTERNAL_CHECK, strerror(errno));
+               _exit(-1);
+       }
+
+       exit_check:
+       elapsed_time++;
+       redraw();
+       signal(SIGALRM, (void *)(battery_check));
+       alarm(bi_interval);
 }
 
-#endif /* linux */
 
diff -Nru xbattbar-1.4.2/xbattbar.man xbattbar-1.4.3/xbattbar.man
--- xbattbar-1.4.2/xbattbar.man 2009-04-23 16:34:54.000000000 +0400
+++ xbattbar-1.4.3/xbattbar.man 2009-04-23 11:55:17.000000000 +0400
@@ -32,6 +32,8 @@
 .Op Fl O Ar color
 .Op Fl i Ar color
 .Op Fl o Ar color
+.Op Fl c
+.Op Fl s Ar script-name
 .Op Ar top | bottom | left | right
 .Sh DESCRIPTION
 .Nm xbattbar
@@ -81,7 +83,18 @@
 .Pp
 .Nm xbattbar
 trys to know its battery status in every 10 seconds in default.
-This is achived by APM polling.
+This is achived by APM polling. If it is used with option
+.Nm -c
+then
+ACPI polling will be used.
+.Pp
+You can use your external script for check battery status. It must print
+two lines to
+.Nm STDOUT
+.Nm 'battery=value'
+and
+.Nm 'ac_line=on|off
+.Pp
 .Nm -p
 option sets the polling interval in second.
 .Pp
@@ -90,14 +103,8 @@
 which shows both AC line status and battery remaining level.
 This diagnosis window disappears if the mouse cursor leaves from
 the status indicator.
-.Sh SEE ALSO
-.Xr xbatt 1
-\- an official battery status check command on BSD/OS 3.0,
-(but it's not fancy).
-.Pp
-.Xr xbattbar-acpi 1
-\- a ligth battery watcher for X11, similar to xbattbar but based an acpi.
 .Sh AUTHOR
 Suguru Yamaguchi <sug...@wide.ad.jp>,
 Akira Kato <k...@wide.ad.jp>,
-Noriyuki Shigechika <n...@wide.ad.jp>
+Noriyuki Shigechika <n...@wide.ad.jp>,
+Dmitry E. Oboukhov <un...@debian.org>

Attachment: signature.asc
Description: Digital signature

Reply via email to