- The added line is THIS COLOR.
- The deleted line is THIS COLOR.
jukeboxのメインスクリプト
#!/bin/sh
#######################
#
# Simple MP3 Jukebox
# KAWAMATA, Yoshihiro
# kaw@on.rim.or.jp
#
#######################
#=====
# utility functions / routines
#=====
# terminate process
#
terminate () {
[ $# -ne 0 ] && echo "$@"
rm -rf ctrl/playing
[ -r ctrl/finish ] && . ctrl/finish
}
# trap for ^C
#
trap 'terminate "Aborted by user" ; exit' 2
# check flags,
# fetch a file,
# play it
#
# Usage: play_one_action { local_file | URL }
#
play_one_action () {
[ $# -eq 0 ] && return
# halt, reboot or exit
#
if [ -f ctrl/halt ]; then
terminate "Halting..."
rm -f ctrl/halt
/sbin/shutdown -hp now
sleep 86400
elif [ -f ctrl/reboot ]; then
terminate "Rebooting..."
rm -f ctrl/reboot
/sbin/shutdown -r now
sleep 86400
elif [ -f ctrl/restart ]; then
terminate "Restarting script..."
rm -f ctrl/restart
exec $progfile
elif [ -f ctrl/exit ]; then
terminate "Exiting..."
rm -f ctrl/exit
exit
fi
# clean non-MP3 file and empty directories under spool
#
if [ -f ctrl/clean ]; then
echo "Clearning dirs..."
rm -f ctrl/clean
find $src $dest oneshot oneshot_finished -type f \! \( -iname '*.mp3' -o -iname
'*.url' \) -print0 | xargs -0 rm -f
for d in $src $dest oneshot oneshot_finished; do
(cd $d && find . -type d -print | sort -r | xargs rmdir >/dev/null 2>&1)
done
fi
# pause playing
#
if [ -f ctrl/pause ]; then
echo "Pausing..."
while [ -f ctrl/pause ]; do
sleep 15
done
fi
# play MP3 file
#
# ... invoke MP3 player with high priority
#
case "$1" in
http://*.mp3|ftp://*.mp3)
#
# Cats are buffers against network stall.
# Please adjust its numbers, if necessary.
#
echo "$1" > ctrl/playing/contents
ftp -o - "$1" |cat|cat|cat| nice -n -15 /usr/local/bin/mpg123 $opts -
;;
*.[Mm][Pp]3)
if [ -f "$1" ]; then
echo "$1" > ctrl/playing/contents
nice -n -15 /usr/local/bin/mpg123 $opts "$1"
else
echo "Cannot find $1"
fi
;;
esac
}
# move played file to another directory.
# directory hierarchy preserved.
#
# Usage: movefile srcpath desttop
#
movefile () {
[ $# -lt 2 ] && return
[ -f $1 ] || return
destdir=$2/${1#*/}
destdir=${destdir%[^/]*}
if [ -d $destdir ]; then
mv $1 $destdir
else
su mp3play -c "mkdir -p $destdir" && mv $1 $destdir
fi
}
#=====
# Running code from here
#=====
# Base and current directory is where script placed.
#
progfile=$0
cd `dirname $progfile` || exit 1
# check if another player running
#
if mkdir ctrl/playing; then
date > ctrl/playing/started
chmod 0755 ctrl/playing
else
echo "Another player running"
exit 1
fi
# remove stale files
#
rm -f ctrl/exit ctrl/reboot ctrl/halt
# user initialization
#
[ -r ctrl/init ] && . ctrl/init
#=====
# main loop ... play MP3 and its control
#=====
while :; do
# parameters to MP3 player
#
unset opts
[ -f ctrl/mpg123opts ] && opts=`cat ctrl/mpg123opts`
# We have two spool directories for infinite loop
# ... spool0 and spool1.
#
# set direction of file movement
# between two spools
# when every MP3 file played
#
if [ -f ctrl/reverse ]; then
src=spool1
dest=spool0
else
src=spool0
dest=spool1
fi
# playlist is symlink to spool for playing.
#
rm -f playlist
ln -s $src playlist
# for every MP3 files
# control and/or playing
#
# xNOPLAY is a sentinel to run inner loop
#
for playfile in xNOPLAY `find $src -type f \( -iname '*.mp3' -o -iname '*.u
rl' \) | sort`; do
# retrieve resource location
#
case "$playfile" in
*.[Uu][Rr][Ll])
mp3reslist=`cat $playfile`
;;
*.[Mm][Pp]3|xNOPLAY)
mp3reslist=$playfile
;;
esac
# for every MP3 resource ...
#
for mp3res in $mp3reslist; do
# perform one shot playlist
#
while :; do
for oneshot in xNOPLAY `find oneshot -type f \( -iname '*.mp3' -o -iname '*.u
rl' \) | sort`; do
# retrieve resource location
#
case "$oneshot" in
*.[Uu][Rr][Ll])
oneshot_mp3res=`cat $oneshot`
;;
*.[Mm][Pp]3|xNOPLAY)
oneshot_mp3res=$oneshot
;;
esac
for os_mp3 in $oneshot_mp3res; do
# check if resource file removed
#
if [ -f $oneshot ]; then
play_one_action $os_mp3
fi
# rescan all contents
#
if [ -f ctrl/rescan ]; then
echo "Rescanning playlist..."
break 5
fi
done
movefile $oneshot oneshot_finished
done
[ X"$oneshot" = XxNOPLAY ] && break
done
play_one_action $mp3res
# restart at current spool
#
if [ -f ctrl/rescan ]; then
echo "Rescanning playlist..."
break 2
fi
done
# move played file to the other spool
#
movefile $playfile $dest
done
# pause when no MP3 files in spools
#
if [ X"$playfile$oneshot" = XxNOPLAYxNOPLAY ]; then
noplay=Z$noplay
echo "No file to play : $noplay"
if [ $noplay = ZZ ]; then
echo "Now sleeping for 60 secs..."
sleep 60
noplay=""
fi
else
noplay=""
fi
# role change of spools
# (not changing when rescan)
#
if [ -f ctrl/rescan ]; then
rm -f ctrl/rescan
else
if [ -f ctrl/reverse ]; then
rm -f ctrl/reverse
else
touch ctrl/reverse
fi
fi
done
----
kqueue / kevent というものを初めて使ってみた;
#include <stdio.h>
#include <sys/types.h>
#include <dirent.h>
#include <sys/types.h>
#include <sys/event.h>
#include <sys/time.h>
main () {
/*
* Open current working directory
*/
DIR *d;
int dfd;
int err;
if (!(d = opendir("."))) {
perror("opendir");
exit(1);
}
/*
* create and register kernel event queue
*/
int kq;
struct kevent kev;
if ((kq = kqueue()) == -1) {
perror("kqueue");
closedir(d);
exit(1);
}
EV_SET(&kev, dirfd(d), EVFILT_VNODE, EV_ADD|EV_CLEAR, NOTE_WRITE, 0, NULL);
if (kevent(kq, &kev, 1, NULL, 0, NULL) < 0) {
perror("kevent on register");
closedir(d);
exit(1);
}
int retval;
/*
* then go monitoring
*/
if (0 < kevent(kq, NULL, 0, &kev, 1, NULL)) {
printf("dir changed.\n");
} else {
perror("kevent on nofity");
closedir(d);
exit(1);
}
/*
* normal exit
*/
closedir(d);
exit(0);
}