grapheqd stands for graphical equalizer daemon. It displays the frequency spectrum of an audio signal via its HTML5 webpage or ASCII based telnet interface. grapheqd runs as a daemon on either Linux with OpenWRT in mind, or FreeBSD. Thus, it uses either ALSA or OSS, choosen at compile time. As FFT computation might require a lot CPU resources on systems without mathematical coprocessor, grapheqd can operate in a client/server mode, where a remote instance on a more powerful system does not use an actual sound device, but connects to a grapheqd instance running on a system with limited CPU power. In such scenarios, you should point your web browser or telnet client only to the remote instance. grapheqd supports PCM signals with one or two channels (read: mono or stereo) and 16 bits per channel. Your audio device must be capable of sampling at 44100 or 48000 Hz. You need a modern web browser with support for JavaScript, CSS3, and websockets in order to access the web interface.
Back in the 80ies and 90ies hifis and stereos came with a graphical equalizer as a separate, physical device, or could be equipped with one. You don't easily find one of these nowadays, at least not for the consumer market. I have never found any use of actually adjusting the audio signal, but always liked the fluorescent dot matrix displays or LCDs. grapheqd tries to reassemble this.
The web interface runs on port 8083 by default:
Point your telnet client to port 8083 as well, and simply enter a c followed by Enter to access the ASCII interface in color mode:
If your terminal does not support colors and/or escape sequences, press m followed by Enter:
grapheqd version 7 PCM driver: OSS Usage: grapheqd [-d] [-e <program>] [-l <address[:port]>] [-p <pidfile>] [-r <address[:port]>] [-s <soundcard>] [-u <user>] grapheqd -h -d run in foreground, and log to stdout/stderr, do not detach from terminal, do not log to syslog -e <program> read PCM data from this program's standard output; the name of the soundcard is passed as first commandline parameter to <program>; if the second commandline parameter is present and has a value of "stderr", i.e. if grapheqd has been started with -d, then <program> can write to standard error safely; otherwise, error logging must be done via syslog, e.g. by calling logger; cannot be used in conjunction with either option -c or -r -l <address[:port]> listen on this address and port; a maximum of 16 addresses may be specified; port defaults to 8083; default: 0.0.0.0:8083 -p <pidfile> daemonize and save pid to this file; no default, pid gets not written to any file unless <pidfile> is given -r <address[:port]> connect to another grapheqd running at this address and port; <port> defaults to 8083; cannot be used in conjunction with either option -e or -s -s <soundcard> read PCM from this soundcard; default: /dev/dsp0; cannot be used in conjunction with option -r; a program given via parameter -e takes precedence -u <user> switch to this user; no default, run as invoking user -h show this help ;-)
$ git clone https://github.com/mborgerding/kissfft.git ../kissfftOr simply call make.
$ make CC=mips-openwrt-linux-gcc
$ git clone https://github.com/felixjogris/grapheqd.gitor grab an official release from this site
$ git clone https://github.com/mborgerding/kissfft.git ../kissfft
grapheqd_enable="YES" grapheqd_profiles="scard remote" grapheqd_scard_soundcard="/dev/dsp1" grapheqd_scard_username="audiouser" grapheqd_remote_address="0.0.0.0:8084" grapheqd_remote_raddress="somehost:8083"You can start each instance via service grapheqd start scard and service grapheqd start remote, respectively. If you omit the profile name, the RC script operates on every configured and enabled instance, e.g. service grapheqd stop.
Create a directory package/grapheqd inside your copy of the OpenWRT source tree, and download openwrt/Makefile to that directory. Now run make menuconfig, and under Multimedia select grapheqd. Optionally, select kmod-usb-audio under Kernel modules -> Sound Support. Then build OpenWRT as usual, e.g. by calling make.
https://github.com/felixjogris/grapheqd/blob/master/openwrt/Makefile is a copy of that Makefile.
$ grapheqd -c <remote host>
mmcc stream tcp nowait root /usr/local/libexec/ffmpeg2grapheqd.sh ffmpeg2grapheqd.sh
# service inetd restart
$ grapheqd -c localhost -r mmcc
Per channel, grapheqd passes 4096 16 bit audio samples (mono or stereo) at a time to FFT, and pushes calculated linear frequency data to all connected clients, thus resulting in roughly 11 or 12 updates per second if your hardware supports sampling at 44100 or 48000 Hz, respectively. The web interface adjusts the labels under each band (vertical bar) to match its frequency range. If only mono audio is available, then the FFT is called just once per loop, while the output data is duplicated. If no client is connected, then no PCM data is read and FFT does not burn CPU cycles unnecessarily.
The internal web serving routines (to put it nicely) use static and predetermined buffers where possible. printf() and family are not used in the hot code paths and loops.