Skip to content

Instantly share code, notes, and snippets.

@charles-l
Last active November 2, 2016 21:27
Show Gist options
  • Select an option

  • Save charles-l/06e01f98be3b50122638914b33cb7723 to your computer and use it in GitHub Desktop.

Select an option

Save charles-l/06e01f98be3b50122638914b33cb7723 to your computer and use it in GitHub Desktop.
a simple notification service demo
// a simple notification daemon that sits on a fifo and calls a popup commend when new lines appear
// to use:
// cc -o notifyd notifyd.c
// ./notifyd
// <in a different terminal>
// echo 'a wild notification appears!' > /etc/notidsock
// <bask in the glory of a simple notification service that's less than 100 lines of code>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
#define MAX_MSG 48
#define FIFOPATH "/tmp/notidsock"
int main(int argc, char **argv) {
char buf[MAX_MSG];
mkfifo(FIFOPATH, 0600);
int fifofd = open(FIFOPATH, O_RDONLY);
while(1) {
size_t bytes = read(fifofd, buf, MAX_MSG);
if(bytes > 0) {
buf[bytes] = '\0'; // set the end of the str (in case it's not filled with zeros)
char *start, *end; // start of line, end of line (so we can do a notification for each line)
start = buf;
while(1) { // popup for each line in the fifo
end = strchr(start, '\n'); // find next newline
if(!end || !*start) // check if we're at the end of the queue
break; // if so, break
end[0] = '\0'; // set the end of the string to the next newline
// NOTE: this is insecure and can be pwned.
// use fork + execve for something real.
char cmd[MAX_MSG + 24]; // 24 more bytes for the command
sprintf(cmd, "popup '%s'", start);
system(cmd);
start = end + 1; // step over \0 to next line
}
}
}
close(fifofd); // heh - maybe cleanup? probably should through this in a signal trap instead
}
#!/bin/sh
#
# z3bra - (c) wtfpl 2014
# Create a small popup with the given text
#
# depends: lemonbar, wattr and common sense
# bar options
#font="-f terminus"
bg="#000000"
fg="#FFFFFF"
hl="#FFFFFF"
strlen=30
default_geometry() {
# get screen size
x=$(wattr w `lsw -r`)
y=$(wattr h `lsw -r`)
width=250
height=20
offy=${2:-$OFF}
offx=$(( x - width ))
echo "${width}x${height}+${offx}+${offy}"
}
while getopts "c:d:g:h" opt; do
case $opt in
d) SLEEP=$OPTARG ;;
g) GEOM=$OPTARG ;;
h) usage; exit 0 ;;
c) COMMAND=$OPTARG ;;
esac
done
GEOM=${GEOM:-$(default_geometry)}
SLEEP=${SLEEP:-5}
if [ -t 0 ]; then
CONTENT=$@
else
CONTENT=$(cat)
fi
str="$CONTENT"
if [ ! -z "$COMMAND" ]; then
str="%{A:$COMMAND:}$str%{A}"
fi
(echo "%{c}" $str; sleep $SLEEP) | lemonbar -d -g $GEOM -B $bg -F $fg $font | sh
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment