On Sun, Jul 28, 2013 at 06:11:39PM +0200, Markus Teich wrote: > Am 2013-07-27 18:27, schrieb Martti Kühne: > >On Mon, Jul 22, 2013 at 3:17 PM, Markus Teich > ><markus.te...@stusta.mhn.de> wrote: > >> > >>rx_now=0 > >>tx_now=0 > >>for i in /sys/class/net/*; do > >> if [[ -d "$i" && ${i##*/} != "lo" ]]; then > >> if [[ -f "$i/statistics/rx_bytes" ]]; then > >> rx_now=($rx_now+`cat $i/statistics/rx_bytes`) > >> fi > >> if [[ -f "$i/statistics/tx_bytes" ]]; then > >> tx_now=($tx_now+`cat $i/statistics/tx_bytes`) > >> fi > >> fi > >>done > >>let rx_rate=($rx_now-$rx_old) > >>let tx_rate=($tx_now-$tx_old) > >> > >Might I ask what shell dialect is that written in? O_o > > Bash patched together with some stackoverflow answers. > It probably is not beautiful, but it works for me until I finally have > the time to write it in C. :/
I included some changes suggested by Markus in a rewrite of the netusage functions for dwmstatus (attached; including an adapted dwmstatus-Makefile for convenience). Comments and criticism is welcome. I will try to push a change request to the suckless sites git repo if nobody threats to neuter my hamster over the code I wrote... Cheers, Silvan
#define _BSD_SOURCE #include <unistd.h> #include <stdbool.h> #include <stdio.h> #include <stdlib.h> #include <stdarg.h> #include <string.h> #include <strings.h> #include <sys/time.h> #include <time.h> #include <sys/types.h> #include <sys/wait.h> #include <X11/Xlib.h> char *tzargentina = "America/Buenos_Aires"; char *tzutc = "UTC"; char *tzberlin = "Europe/Berlin"; static Display *dpy; char * smprintf(char *fmt, ...) { va_list fmtargs; char *ret; int len; va_start(fmtargs, fmt); len = vsnprintf(NULL, 0, fmt, fmtargs); va_end(fmtargs); ret = malloc(++len); if (ret == NULL) { perror("malloc"); exit(1); } va_start(fmtargs, fmt); vsnprintf(ret, len, fmt, fmtargs); va_end(fmtargs); return ret; } void settz(char *tzname) { setenv("TZ", tzname, 1); } int parse_netdev(unsigned long long int *receivedabs, unsigned long long int *sentabs) { char buf[255]; char *datastart; static int bufsize; int rval; FILE *devfd; unsigned long long int receivedacc, sentacc; bufsize = 255; devfd = fopen("/proc/net/dev", "r"); rval = 1; // Ignore the first two lines of the file fgets(buf, bufsize, devfd); fgets(buf, bufsize, devfd); while (fgets(buf, bufsize, devfd)) { if ((datastart = strstr(buf, "lo:")) == NULL) { datastart = strstr(buf, ":"); // With thanks to the conky project at http://conky.sourceforge.net/ sscanf(datastart + 1, "%llu %*d %*d %*d %*d %*d %*d %*d %llu",\ &receivedacc, &sentacc); *receivedabs += receivedacc; *sentabs += sentacc; rval = 0; } } fclose(devfd); return rval; } void calculate_speed(char *speedstr, unsigned long long int newval, unsigned long long int oldval) { double speed; speed = (newval - oldval) / 1024.0; if (speed > 1024.0) { speed /= 1024.0; sprintf(speedstr, "%.3f MB/s", speed); } else { sprintf(speedstr, "%.2f KB/s", speed); } } char * get_netusage(unsigned long long int *rec, unsigned long long int *sent) { unsigned long long int newrec, newsent; newrec = newsent = 0; char downspeedstr[15], upspeedstr[15]; static char retstr[42]; int retval; retval = parse_netdev(&newrec, &newsent); if (retval) { fprintf(stdout, "Error when parsing /proc/net/dev file.\n"); exit(1); } calculate_speed(downspeedstr, newrec, *rec); calculate_speed(upspeedstr, newsent, *sent); sprintf(retstr, "down: %s up: %s", downspeedstr, upspeedstr); *rec = newrec; *sent = newsent; return retstr; } char * mktimes(char *fmt, char *tzname) { char buf[129]; time_t tim; struct tm *timtm; bzero(buf, sizeof(buf)); settz(tzname); tim = time(NULL); timtm = localtime(&tim); if (timtm == NULL) { perror("localtime"); exit(1); } if (!strftime(buf, sizeof(buf)-1, fmt, timtm)) { fprintf(stderr, "strftime == 0\n"); exit(1); } return smprintf("%s", buf); } void setstatus(char *str) { XStoreName(dpy, DefaultRootWindow(dpy), str); XSync(dpy, False); } char * loadavg(void) { double avgs[3]; if (getloadavg(avgs, 3) < 0) { perror("getloadavg"); exit(1); } return smprintf("%.2f %.2f %.2f", avgs[0], avgs[1], avgs[2]); } int main(void) { char *status; char *avgs; char *tmar; char *tmutc; char *tmbln; char *netstats; static unsigned long long int rec, sent; if (!(dpy = XOpenDisplay(NULL))) { fprintf(stderr, "dwmstatus: cannot open display.\n"); return 1; } parse_netdev(&rec, &sent); for (;;sleep(1)) { avgs = loadavg(); tmar = mktimes("%H:%M", tzargentina); tmutc = mktimes("%H:%M", tzutc); tmbln = mktimes("KW %W %a %d %b %H:%M %Z %Y", tzberlin); netstats = get_netusage(&rec, &sent); status = smprintf("[L: %s|N: %s|A: %s|U: %s|%s]", avgs, netstats, tmar, tmutc, tmbln); setstatus(status); free(avgs); free(tmar); free(tmutc); free(tmbln); free(status); } XCloseDisplay(dpy); return 0; }
# See LICENSE file for copyright and license details. include config.mk SRC = ${NAME}.c OBJ = ${SRC:.c=.o} all: options ${NAME} options: @echo ${NAME} build options: @echo "CFLAGS = ${CFLAGS}" @echo "LDFLAGS = ${LDFLAGS}" @echo "CC = ${CC}" .c.o: @echo CC $< @${CC} -c ${CFLAGS} $< ${OBJ}: config.mk ${NAME}: ${OBJ} @echo CC -o $@ @${CC} -o $@ ${OBJ} ${LDFLAGS} clean: @echo cleaning @rm -f ${NAME} ${OBJ} ${NAME}-${VERSION}.tar.gz dist: clean @echo creating dist tarball @mkdir -p ${NAME}-${VERSION} @cp -R Makefile config.mk LICENSE \ ${SRC} ${NAME}-${VERSION} @tar -cf ${NAME}-${VERSION}.tar ${NAME}-${VERSION} @gzip ${NAME}-${VERSION}.tar @rm -rf ${NAME}-${VERSION} install: all @echo installing executable file to ${DESTDIR}${PREFIX}/bin @mkdir -p ${DESTDIR}${PREFIX}/bin @cp -f ${NAME} ${DESTDIR}${PREFIX}/bin @chmod 755 ${DESTDIR}${PREFIX}/bin/${NAME} uninstall: @echo removing executable file from ${DESTDIR}${PREFIX}/bin @rm -f ${DESTDIR}${PREFIX}/bin/${NAME} .PHONY: all options clean dist install uninstall
NAME = dwmstatus-netusage VERSION = 1.2 # Customize below to fit your system # paths PREFIX = /usr/local MANPREFIX = ${PREFIX}/share/man X11INC = /usr/X11R6/include X11LIB = /usr/X11R6/lib # includes and libs INCS = -I. -I/usr/include -I${X11INC} LIBS = -L/usr/lib -lc -L${X11LIB} -lX11 # flags CPPFLAGS = -DVERSION=\"${VERSION}\" CFLAGS = -g -std=c99 -pedantic -Wall -O0 ${INCS} ${CPPFLAGS} #CFLAGS = -std=c99 -pedantic -Wall -Os ${INCS} ${CPPFLAGS} LDFLAGS = -g ${LIBS} #LDFLAGS = -s ${LIBS} # Solaris #CFLAGS = -fast ${INCS} -DVERSION=\"${VERSION}\" #LDFLAGS = ${LIBS} # compiler and linker CC = cc
pgp0n5W3dEW9R.pgp
Description: PGP signature