wally fatboy klingon
Fight ePatents in Europe!
Get FireFox
I'm a hacker!
Valid CSS!
Valid HTML 4.01!
 
Now, you and your roommate can terrorize your other roommates with loud music. This script can play a MP3 file completely synchronously on two separate computers. Well, actually both computers need a good network connection and fast enough CPU. But it works for me, and maybe you'll like to try it out. [download]
#!/bin/sh
#########

# SSNA: Synchonious Streaming Network Audio
#
# Functionality: Play one MP3 on two hosts synchroniously
#    (It can play from fifo's too!)
#
# Requirements: 1) A fast network
#               2) The 'nc' (netcat) utility somewhere in your path
#               3) An MP3 file
#               4) Two hosts would be nice, although one will work too
#               5) sh, cut, cat, grep, ps, ifconfig, rm, mkdir, mknod, kill
#
# ChangeLog:
#  v4: added --clean to clean up leftover netcat/cat sessions
#  v3: protects against root running this script
#  v2: accepts MP3-files with spaces in the name
#  v1: first release

echo "SSNA - Synchonious Streaming Network Audio version 4"
echo "Copyright (C) 2001 S. Smeenk"
echo "This software is released under the GPL license"
echo

# Protection against root running this script...
IDGREP=`id | grep "uid=0"`
if [ "x$IDGREP" != "x" ]; then
	echo " ! Never run this shellscript as root please..."
fi

if [ "x$1" == "x--clean" ]; then
	echo " * Cleaning up leftover netcat & cat sessions as you requested..."
	LGO=`ps ax | grep "nc -l -p 31331" | grep -v grep | cut -b 1-5`
	LGT=`ps ax | grep "nc -l -p 31332" | grep -v grep | cut -b 1-5`
	CGO=`ps ax | grep "cat /tmp/SSNA/host1" | grep -v grep | cut -b 1-5`
	CGT=`ps ax | grep "cat /tmp/SSNA/host2" | grep -v grep | cut -b 1-5`
	if [ "$LGO" ] || [ "$LGT" ] || [ "$CGO" ] || [ "$CGT" ]; then
	    echo " ? Found netcat or cat leftovers ..."
	    echo "   Killing them..."
	    kill $LGO $LGT $CGO $CGT 2>&1 >/dev/null
	fi
	echo " - Done ..."
	exit 0
fi

# Check the essential parameters...
if [ "x$1" == "x" ]; then
	echo "Usage: ./SSNA.sh [ <mp3-file> | --clean ] [--one]"
	echo -e "Example: ./SSNA.sh ~/music.mp3\n"
	echo "   --one: run test with one listening host on port 31331"
	echo -e "   --clean: clean up leftover netcat & cats after C-c'ing out\n";
	exit 255
fi

# Check if the file is > 0 bytes, exists and is readable for you ...
if [ ! -s "$1" ] || [ ! -e "$1" ] || [ ! -r "$1" ]; then
	echo "Access error to $1..."
	#exit 255
fi

# Find out the local IP for display purposes only...
LOCALIP=`ifconfig eth0 | grep inet | sed -e 's/ /:/g' | cut -d':' -f13`
if [ "x$LOCALIP" == "x" ]; then
	echo -e "Hmm.. Couldn't figure out your local IP address! (non-fatal)\n"
	LOCALIP='thishost'
fi

# Try to create fifo's...
echo " * Creating temporary directory /tmp/SSNA, and fifo's ..."
if [ -e /tmp/SSNA ] && [ -d /tmp/SSNA ]; then
	echo " ? Looks like there is leftover SSNA runs still here..."
	echo "   Trying to removing them ..."
	set +e
	rm -r /tmp/SSNA
	set -e
fi
mkdir /tmp/SSNA
mknod /tmp/SSNA/host1 p
mknod /tmp/SSNA/host2 p

# Sets up the listening netcat services on ports 31331 and 31332
# Also kills leftover netcat sessions...
echo " * Setting up listening netcats in the background ..."
LGO=`ps ax | grep "nc -l -p 31331" | grep -v grep | cut -b 1-5`
LGT=`ps ax | grep "nc -l -p 31332" | grep -v grep | cut -b 1-5`
CGO=`ps ax | grep "cat /tmp/SSNA/host1" | grep -v grep | cut -b 1-5`
CGT=`ps ax | grep "cat /tmp/SSNA/host2" | grep -v grep | cut -b 1-5`
if [ "$LGO" ] || [ "$LGT" ] || [ "$CGO" ] || [ "$CGT" ]; then
	echo " ? Found netcat or cat leftovers ..."
	echo "   Killing them..."
	kill $LGO $LGT $CGO $CGT 2>&1 >/dev/null
fi
cat /tmp/SSNA/host1 | nc -l -p 31331 &
cat /tmp/SSNA/host2 | nc -l -p 31332 &

# Asks for user to start the connecting netcat | mpg123 -
echo " * Start listening on this host, ports 31331 and 31332!"
echo "    For the first host:  nc $LOCALIP 31331 | mpg123 -"
echo "    For the second host: nc $LOCALIP 31332 | mpg123 -"
echo " + Press enter if the two hosts are connected..."
read

# Cats the file through tee which puts the data in fifo 1 and 2
# Unless user specified a ARGV[2], in that case only use fifo 1
echo " * Streaming the file... (you should hear audio now)"
if [ "x$2" != "x" ]; then
	cat "$1" > /tmp/SSNA/host1
else
	cat "$1" | tee /tmp/SSNA/host1 > /tmp/SSNA/host2
fi

# Kill the netcat & cat sessions and remove the temporary directory...
echo " * Cleaning up..."
LGO=`ps ax | grep "nc -l -p 31331" | grep -v grep | cut -b 1-5`
LGT=`ps ax | grep "nc -l -p 31332" | grep -v grep | cut -b 1-5`
CGO=`ps ax | grep "cat /tmp/SSNA/host1" | grep -v grep | cut -b 1-5`
CGT=`ps ax | grep "cat /tmp/SSNA/host2" | grep -v grep | cut -b 1-5`
if [ "$LGO" ] || [ "$LGT" ] || [ "$CGO" ] || [ "$CGT" ]; then
	kill $LGO $LGT $CGO $CGT 2>&1 >/dev/null
fi
set +e
rm -r /tmp/SSNA
set -e

# And we are done...
echo " - Done..."