Madplay on an Intel Mac
Numerous MP3 players around my house pull music from a central file server. The hardware I'm using is extremely diverse and many devices can nowadays be politely described as junk: they include 100MHz Pentiums with 16MB RAM, and an ARM-based prototype lacking support for floating point operations. For the sake of simplicity I've standardized the setups around a web server running on each machine to list static HTML pages containing the available music files, and simple shell-based CGI clients that invoke madplay to play the music. When I added an Intel-based Mac to the mix I found that madplay refused to work, producing only a white noise hiss.
Initially I had cross-compiled madplay from source on a PowerPC machine as a Mach-O fat binary running on both Intel and PowerPC architectures. For this I configured the software using commands like the following.
CFLAGS='-arch i386 -arch ppc' ./configure -disable-dependency-tracking'
At that point I abandoned madplay and decided to try my luck
with VLC.
This however proved unwieldy for my purposes.
Controlling it from CGI shell scripts required opening a Unix-domain
socket, and, according to dtruss, it seemed to ignore the
no-auto-preparse
and no-mmap
command-line
options somehow
bringing my (severely underpowered) NFS server to its knees by issuing many
erroneous NFS requests.
I thought I could dig into this problem and fix it, but
the source code of VLC brought tears to my eyes, so I decided to abandon
that avenue.
After a night's sleep I got up convinced that madplay's white noise was a simple endianess problem, which I could easily solve. A simple grep for the word endian in the source code showed me that there were corresponding preprocessor conditionals, like the following
# if defined(WORDS_BIGENDIAN)
Fixing the problem was trivial. Here is the corresponding patch.
diff -u -r1.1 audio_carbon.c
--- audio_carbon.c 2009/07/13 06:57:51 1.1
+++ audio_carbon.c 2009/07/13 06:58:57
@@ -234,7 +234,11 @@
break;
case 16:
+# if defined(WORDS_BIGENDIAN)
audio_pcm = audio_pcm_s16be;
+# else
+ audio_pcm = audio_pcm_s16le;
+# endif
break;
}