Skip to content
Snippets Groups Projects
Commit 0ab80500 authored by Martin Mareš's avatar Martin Mareš
Browse files

Cleaned up utility functions and implemented `osd-batt --check-every'

parent 6b006900
Branches
No related tags found
No related merge requests found
......@@ -3,8 +3,8 @@ CFLAGS=-O2 -Wall -W -Wno-parentheses -Wstrict-prototypes -Wmissing-prototypes -W
all: osdd osdc osd-batt
osdd: osdd.o util.o
osdc: osdc.o util.o send.o
osd-batt: osd-batt.o util.o send.o
osdc: osdc.o util.o client.o
osd-batt: osd-batt.o util.o client.o loop.o
osdd.o: CFLAGS+=$(shell xosd-config --cflags)
osdd: LDFLAGS+=$(shell xosd-config --libs)
......
/*
* On-screen Display Client -- Sending Messages
* On-screen Display -- Support Functions for Clients
*
* (c) 2010 Martin Mares <mj@ucw.cz>
*/
......@@ -7,11 +7,13 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <poll.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include "util.h"
#include "send.h"
#undef DEBUG
#include "osd.h"
static Display *dpy;
static Atom pty;
......@@ -26,6 +28,9 @@ struct osd_msg {
void
osd_init(void)
{
if (dpy)
return;
dpy = XOpenDisplay(NULL);
if (!dpy)
die("Cannot open display");
......@@ -56,12 +61,50 @@ osd_add_line(struct osd_msg *msg, char *key, char *val)
void
osd_send(struct osd_msg *msg)
{
if (!dpy)
osd_init();
msg->buf[msg->cnt++] = '\n';
if (!XChangeProperty(dpy, DefaultRootWindow(dpy), pty, XA_STRING, 8, PropModeAppend, (unsigned char *) msg->buf, msg->cnt))
die("XChangeProperty failed");
XFlush(dpy);
free(msg);
}
void
osd_fork(void)
{
osd_init();
pid_t pid = fork();
if (pid < 0)
die("Cannot fork: %m");
if (pid > 0)
exit(0);
setsid();
}
void
osd_wait(int delay)
{
DBG("Waiting for %d seconds\n", delay);
timestamp_t wait_until = get_current_time() + delay*1000;
struct pollfd pfd = {
.fd = ConnectionNumber(dpy),
.events = POLLIN,
};
for (;;)
{
timestamp_t now = get_current_time();
if (now >= wait_until)
return;
DBG("... waiting for %d ms\n", (int)(wait_until - now));
poll(&pfd, 1, wait_until - now);
if (pfd.revents & POLLIN)
{
XEvent ev;
while (XPending(dpy))
XNextEvent(dpy, &ev);
}
}
}
......@@ -11,10 +11,10 @@
#include <dirent.h>
#include <getopt.h>
#include "util.h"
#include "send.h"
#include "osd.h"
static int check_mode;
static int check_every;
static int warn_threshold = 600;
static int total_full, total_capa, discharge_rate;
......@@ -202,6 +202,12 @@ static void show(void)
osd_send(msg);
}
static void show_if_warn(void)
{
if (discharge_mask && discharge_time < warn_threshold)
show();
}
static void NONRET
usage(void)
{
......@@ -210,15 +216,17 @@ Usage: osd-batt <options>\n\
\n\
Options:\n\
-c, --check\t\tDisplay status only if battery is low\n\
-e, --check-every=<sec>\tRun on background and check every <sec> seconds\n\
-w, --warn=<sec>\tBattery is low if less than <sec> seconds remain (default: 600)\n\
");
exit(1);
}
static const char short_opts[] = "cw:";
static const char short_opts[] = "ce:w:";
static const struct option long_opts[] = {
{ "check", no_argument, NULL, 'c' },
{ "check-every", required_argument, NULL, 'e' },
{ "warn", required_argument, NULL, 'w' },
{ NULL, 0, NULL, 0 },
};
......@@ -232,6 +240,9 @@ int main(int argc, char **argv)
case 'c':
check_mode++;
break;
case 'e':
check_every = atoi(optarg);
break;
case 'w':
warn_threshold = atoi(optarg);
break;
......@@ -241,8 +252,21 @@ int main(int argc, char **argv)
if (optind < argc)
usage();
if (check_every)
{
osd_fork();
for (;;)
{
scan();
show_if_warn();
osd_wait(check_every);
}
}
scan();
if (!check_mode || (discharge_mask && discharge_time < warn_threshold))
if (check_mode)
show_if_warn();
else
show();
return 0;
......
......@@ -4,9 +4,15 @@
* (c) 2010 Martin Mares <mj@ucw.cz>
*/
#include <inttypes.h>
#define NONRET __attribute__((noreturn))
#define FORMAT_CHECK(func,i,j) __attribute__((format(func,i,j)))
typedef uint64_t timestamp_t;
/* util.c */
void NONRET FORMAT_CHECK(printf,1,2) die(char *fmt, ...);
#ifdef DEBUG
......@@ -16,3 +22,17 @@ void NONRET FORMAT_CHECK(printf,1,2) die(char *fmt, ...);
#endif
void *xmalloc(int size);
timestamp_t get_current_time(void);
/* client.c */
void osd_init(void);
struct osd_msg;
struct osd_msg *osd_new_msg(void);
void osd_add_line(struct osd_msg *msg, char *key, char *val);
void osd_send(struct osd_msg *msg);
void osd_fork(void);
void osd_wait(int seconds);
......@@ -11,8 +11,7 @@
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include "util.h"
#include "send.h"
#include "osd.h"
static struct osd_msg *msg;
......
......@@ -8,20 +8,17 @@
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <inttypes.h>
#include <poll.h>
#include <getopt.h>
#include <sys/time.h>
#include <xosd.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#undef DEBUG
#include "util.h"
#include "osd.h"
static xosd *osd;
typedef uint64_t timestamp_t;
static timestamp_t now;
/*** Options ***/
......@@ -246,10 +243,7 @@ main(int argc, char **argv)
{
pid_t pid = fork();
if (pid < 0)
{
fprintf(stderr, "batt: Cannot fork: %m\n");
return 1;
}
die("Cannot fork: %m");
if (pid > 0)
return 0;
setsid();
......@@ -274,9 +268,7 @@ main(int argc, char **argv)
for (;;)
{
struct timeval tv;
gettimeofday(&tv, NULL);
now = (timestamp_t) tv.tv_sec * 1000 + tv.tv_usec / 1000;
now = get_current_time();
timestamp_t wait_until = now - 1;
if (!current_msg && first_msg)
......
/*
* On-screen Display Client -- Sending Messages
*
* (c) 2010 Martin Mares <mj@ucw.cz>
*/
void osd_init(void);
struct osd_msg;
struct osd_msg *osd_new_msg(void);
void osd_add_line(struct osd_msg *msg, char *key, char *val);
void osd_send(struct osd_msg *msg);
......@@ -7,8 +7,9 @@
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <sys/time.h>
#include "util.h"
#include "osd.h"
void __attribute__((noreturn)) __attribute__((format(printf,1,2)))
die(char *fmt, ...)
......@@ -29,3 +30,11 @@ xmalloc(int size)
die("Failed to allocate %d bytes of memory", size);
return p;
}
timestamp_t
get_current_time(void)
{
struct timeval tv;
gettimeofday(&tv, NULL);
return (timestamp_t) tv.tv_sec * 1000 + tv.tv_usec / 1000;
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment