3

I've got a bunch of WAV files and a script that copies them to another directory, but processes some of the files with SoX. The outputted files should all have 1 channel and have a sample rate of 44.1khz or less. Most of my files either have more than one channel or the sample rate is greater 44.1khz, but only 3 files have both. When converting those 3 files with the code snippet below, I get the "sox WARN wav: Premature EOF on .wav input file" error.

# $x is the filename + extension
# $2 is the destination folder
convertedWAV=false
hz=$(sox --info $PWD/$x | sed -n 4p | tr ' ' '\n' | tail -1)
chan=$(sox --info $PWD/$x | sed -n 3p | tr ' ' '\n' | tail -1)

# If its more than 44.1khz, then bring it down to that
if [[ $hz > 44100 ]]; then
    echo "ADJUSTING HZ"
    convertedWAV=true
    sox $PWD/$x --rate 44100 $2/$x
fi

# If its more than 1 channel (AKA Stereo), then reduce it.
if [[ $chan > 1 ]]; then
    echo "ADJUSTING CHANNELS"
    if [[  $convertedWAV == false ]]; then
        sox $PWD/$x --channels 1 $2/$x
    else
        sox $2/$x --channels 1 $2/$x
    fi
    convertedWAV=true
fi

if [[ $convertedWAV == false ]]; then
    ln "$PWD/$x" "$2"
fi

Notice how those 3 files went through two separate SoX commands. I then modified my script so if both channels > 1 and hz > 44100 then it does a single sox command, code seen below.

if [[ $chan > 1 ]] && [[ $hz > 44100 ]]; then
    sox $PWD/$x --channels 1 --rate 44100 $2/$x
elif [[ $chan > 1 ]]; then
    sox $PWD/$x --channels 1 $2/$x
elif [[ $hz > 44100 ]]; then
    sox $PWD/$x --rate 44100 $2/$x
else
    cp "$PWD/$x" "$2/$x"
fi

This now works. My question is, why? It behaves the same if I do sox $PWD/$x --rate 44100 --channels 1 $2/$x, for some reason doing it in two commands causes an issue. I can't find a definite answer. According to this the error can happen because the hdr's length isn't actually the length, so maybe the first SoX command corrupts the file slightly? I don't know if this is a bug with SoX's conversions or something wrong with my audio file/s. I've uploaded one of them here incase that helps.

Protofall
  • 612
  • 1
  • 6
  • 15

1 Answers1

2

sox $2/$x --channels 1 $2/$x

You can't concat the file $2/$x onto itself.

Seth
  • 707
  • 1
  • 9
  • 20
  • Oh, I thought that was taking the 1st file as source, outputting into some temp file, then copy-saving it with the 2nd filename. I didn't realise it just skipped the temp file. I'll need to re-setup my dev environment to test this, but thanks for clarifying. – Protofall Aug 01 '21 at 04:08
  • No, that would be super convenient, but unfortunately you have to do that manually, I couldn't even find an optional flag... Anyway, I hope you mark the answer as right if/when you test it, I have yet to have a single one marked as right ;) – Seth Aug 18 '21 at 20:31
  • 1
    I'm so busy these day's that it will take me months to get around to trying this out. The answer makes sense though, so I'll mark it as the accepted answer. Thanks again for the insight. – Protofall Aug 23 '21 at 09:16