#!/bin/bash # === some global setting & configurations for the script === umask 000 # create files with all right for anyone shopt -s nullglob # expand patterns which match no file to a null string shopt -s extdebug # -------------------------------------------------------------- # das Verzeichnis in dem dieses script liegt herausfinden scriptDir=${0%/*} scriptDir="${scriptDir/#\./${PWD}}" case "${scriptDir}" in /*);; *) scriptDir="${PWD}/${scriptDir}";; esac # -------------------------------------------------------------- # include helpers . ${scriptDir}/shellUtils.sh # -------------------------------------------------------------- # string definitions usage=$"usage: $0 [-t {m|f|o}] [-p path] [-e encoder] [-c cddb-entry] [-h|-?] [-I interface] [-D device] [-v[v]] \t-t: you can specify either m for encoding to mp3 \t using lame, or f for making lossless encoding using flac, \t or o for making ogg/vorbis, or w for uncompressed wav. \t Omitting this results in encoding to flac. \t mp3s will be placed under a subfolder mp3 and flacs \t under a subfolder flac \t-p: specifies the path to save the encoded data. \t Defaults to the users home directory. \t-e: specifies the mp3 encoder to use. \t valid encoders are actually: lame,bladeenc \t Defaults to lame. \t-c: specifies the CDDB-Entry to use. \t sometimes there is more than 1 entry for a cd in cddb. \t Then you can specify wich one to use by this option. \t You can checkout all entries using cddb.pl. \t-I: specifies cdda2wav interface to use. \t Valid interfaces are generic_scsi and cooked_ioctl. \t Please note that cooked_ioctl is not available on all systems. \t Defaults to generic_scsi \t-D: specifies device to use with cdda2wav. \t Defaults to /dev/cdrom \t-v: make the script more verbose. The verbosity level defaults \t to 1. When -v is given the level is 2 and -vv increases the \t level to 3, what means give debug output. \t-q: make the script silent. Equivalent to -v0 \t-h| \t-?: Shows this help." ready=$"done" # level 1 messages getCDInfoMsg=$"getting cd info..." outputDirMsg=$"output to: \$encodingDir" createXmlMsg=$"create xml file..." startRipMsg1=$"start ripping cd audio data..." # level 2 messages encodeMp3Msg=$"Encode to mp3" encodeFlacMsg=$"Encode to flac" encodeOggMsg=$"Encode to ogg" encodeWavMsg=$"Encode to wav" startRipMsg2=$"start ripping cd audio data:" cdInfoMsg=$"DISK: ===== Tracks: \$dTracks Length: \$dLength Index: \$dIndex Artist: \$dArtist Title: \$dTitle Year: \$dYear Genre: \$dGenre CDDB: \$cddbId Text: \$dText Extra: \$dExtra TRACKS: =======" # -------------------------------------------------------------- taOrder="t" encodingDir=$HOME encodingType="f" encoder="lame" cddbEntry=1 cddaIf="generic_scsi" cddaDev="/dev/cdrom" verbose=1 # ---------------------------------------------------------------- # get commandline options while getopts qvt:p:he:c:I:D: option do case $option in t) if [ "${OPTARG}" != "m" -a "${OPTARG}" != "f" -a \ "${OPTARG}" != "o" -a "${OPTARG}" != "w" ] then echo -e "$usage" exit 1 fi encodingType=$OPTARG ;; p) if [ ! \( -d ${OPTARG} \) ] then echo -e "$usage" exit 1 fi encodingDir=$OPTARG ;; e) if [ -z ${OPTARG} ] then echo -e "$usage" exit 1 fi encoder=$OPTARG ;; c) if [ ${OPTARG} -lt 1 ] then echo -e "$usage" exit 1 fi cddbEntry=$OPTARG ;; v) if [ "${OPTARG}" -a "${OPTARG}" != "0" -a "${OPTARG}" != "v" ] then echo -e "$usage" exit 1 fi test -z "${OPTARG}" && verbose=2 test "${OPTARG}" = "0" && verbose=0 test "${OPTARG}" = "v" && verbose=3 ;; q) verbose=0 ;; I) if [ "${OPTARG}" != "generic_scsi" -a \ "${OPTARG}" != "cooked_ioctl" ] then echo -e "$usage" exit 1 fi cddaIf=$OPTARG ;; D) if [ ${OPTARG} -lt 1 ] then echo -e "$usage" exit 1 fi cddaDev=$OPTARG ;; [h\?]) echo -e "$usage" exit 1 ;; esac done # ---------------------------------------------------------------- echo "verbose: $verbose" # ---------------------------------------------------------------- # set encodingDir for used encodingType case ${encodingType} in m) encodingDir="$encodingDir/mp3" test ${verbose} -ge 2 && echo ${encodeMp3Msg} ;; f) encodingDir="$encodingDir/flac" test ${verbose} -ge 2 && echo ${encodeFlacMsg} ;; o) encodingDir="$encodingDir/ogg" test ${verbose} -ge 2 && echo ${encodeOggMsg} ;; w) encodingDir="$encodingDir/wav" test ${verbose} -ge 2 && echo ${encodeWavMsg} ;; esac # ---------------------------------------------------------------- test ${verbose} -ge 1 && echo -n ${getCDInfoMsg} getCDInfo # gets all info about the CD. Look in shellUtils for more info. test ${verbose} -ge 1 && echo ${ready} if [ ${verbose} -ge 2 ] then cat <<-EOF $cdInfoMsg EOF i=0 while [ $i -lt ${#tTitle[@]} ] do echo -n "${tArtist[$i]} - ${tTitle[$i]} " echo "([${tStartSec[$i]}-${tEndSec[$i]}] ${tLength[$i]})" i=$((i+1)) done fi encodingDir="${encodingDir}/${dArtist}/${dTitle}" mkdir -p "${encodingDir}" test ${verbose} -ge 1 && eval "echo ${outputDirMsg}" # ---------------------------------------------------------------- # fill xml file with data test ${verbose} -ge 1 && echo -n "${createXmlMsg}" xmlFile="${encodingDir}/cdinfo.xml" xml_dText="`echo "${dText}" | recode utf8..h0`" xml_dExtra="`echo "${dExtra}" | recode utf8..h0`" xml_dArtist="`echo "${dArtist}" | recode utf8..h0`" xml_dTitle="`echo "${dTitle}" | recode utf8..h0`" cat >"${xmlFile}" < ${dIndex} ${cddbId} ${xml_dText} ${xml_dExtra} ${xml_dArtist} ${xml_dTitle} ${dYear} ${dGenre} ${dLength} ${dTracks} EOF i=0 while [ $i -lt ${#tTitle[@]} ] do trackNr="`printf %02d $((i+1))`" xml_tTitle="`echo ${tTitle[$i]} | recode utf8..h0`" xml_tArtist="`echo ${tArtist[$i]} | recode utf8..h0`" trackEnd=${tEndSec[$i]} trackStart=${tStartSec[$i]} trackLen=$((trackEnd-$trackStart)) cat >>"${xmlFile}" < $trackNr ${tLength[$i]} ${tStartSec[$i]} ${trackLen} $xml_tArtist $xml_tTitle EOF i=$((i+1)) done echo "" >>"${xmlFile}" test ${verbose} -ge 1 && echo "${ready}" # ---------------------------------------------------------------- # ---------------------------------------------------------------- # now do the ripping test ${verbose} -eq 1 && echo -n "${startRipMsg1}" test ${verbose} -ge 2 && echo "${startRipMsg2}" i=0 while [ $i -lt ${#tTitle[@]} ] do trackNr=$((i+1)) # now that i don't forget it again. I use tr to translate \r to \n # because sed does't recognise a line with only \r at its end as a line. # Therefor sed reads until output of cdda2wav ends and does all the # processing at once, so the percentage is not shown correctly if [ ${verbose} -ge 2 ] then outCmd="tr '\r' '\n' | sed '/^ [0-9]/!d;s/^.* \([0-9]*%\).*$/\r'\"\${outStr}\"'\1/' | tr -d '\n'" else outCmd="cat >/dev/null" fi case ${encodingType} in f) outFile="`printf %02d ${trackNr}`-${tTitle[$i]}.flac" outStr="track-$trackNr => ${outFile}: " ( exec 2>&1 cdda2wav -H -D/dev/cdrom -I${cddaIf} -t${trackNr} - |\ flac -c -f \ -T artist="${tArtist[$i]}" -T album="${dTitle}" \ -T genre="${dGenre}" -T title="${tTitle[$i]}" \ -T tracknumber="${trackNr}" -T tracknum="${trackNr}" \ -T date="${dYear}" -T comment="" \ -o "${encodingDir}/${outFile}" - 2>/dev/null ) | $outCmd ;; m) outFile="`printf %02d ${trackNr}`-${tTitle[$i]}.mp3" outStr="track-$trackNr => ${outFile}: " case ${encoder} in lame) ( exec 2>&1 cdda2wav -H -D/dev/cdrom -I${cddaIf} -t${trackNr} - |\ lame -V2 \ --ta "${tArtist[$i]}" --tl "${dTitle}" \ --tg "${dGenre}" --tt "${tTitle[$i]}" \ --tn "${trackNr}" --ty "${dYear}" \ --tc "" \ - "${encodingDir}/${outFile}" 2>/dev/null ) | tr '\r' '\n' |\ sed '/^ [0-9]/!d;s/^.* \([0-9]*%\).*$/\r'"${outStr}"'\1/' |\ tr -d '\n' ;; bladeenc) ( exec 2>&1 cdda2wav -H -D/dev/cdrom -I${cddaIf} -t${trackNr} - |\ bladeenc -progress=0 STDIN \ "${encodingDir}/${outFile}" 2>/dev/null ) | tr '\r' '\n' |\ sed '/^ [0-9]/!d;s/^.* \([0-9]*%\).*$/\r'"${outStr}"'\1/' |\ tr -d '\n' ;; esac ;; o) outFile="`printf %02d ${trackNr}`-${tTitle[$i]}.ogg" outStr="track-$trackNr => ${outFile}: " ( exec 2>&1 cdda2wav -H -D/dev/cdrom -I${cddaIf} -t${trackNr} - |\ oggenc -a "${tArtist[$i]}" -l "${dTitle}" \ -G "${dGenre}" -t "${tTitle[$i]}" \ -N "${trackNr}" -d "${dYear}" \ -c "" \ -o "${encodingDir}/${outFile}" - 2>/dev/null ) | tr '\r' '\n' |\ sed '/^ [0-9]/!d;s/^.* \([0-9]*%\).*$/\r'"${outStr}"'\1/' |\ tr -d '\n' ;; w) outFile="`printf %02d ${trackNr}`-${tTitle[$i]}.wav" outStr="track-$trackNr => ${outFile}: " ( exec 2>&1 cdda2wav -H -D/dev/cdrom -I${cddaIf} -t${trackNr} - >\ "${encodingDir}/${outFile}" ) | tr '\r' '\n' |\ sed '/^ [0-9]/!d;s/^.* \([0-9]*%\).*$/\r'"${outStr}"'\1/' |\ tr -d '\n' ;; esac echo # do a newline after each file i=$((i+1)) done test ${verbose} -eq 1 && echo "${ready}" # ----------------------------------------------------------------