Streaming MPEG-4 with Linux
Here at my school video clips are stored in different formats. This is likely to be the case in most situations--you do not need to convert only one format to MPEG-4 but many formats. Some of my fellow video team members store the clips in MPEG-1 and 2, some of them in DivX or XviD AVI and some use DV AVI if they do not have time to encode. Here, we discuss how we encode these formats to MPEG-4, as they are likely to be the most common formats we might come across.
No single tool with a single button can do all the encoding work well for you. You need to encode the video and audio separately, so the first thing to do is split up the video and audio. Under Linux, FFmpeg is a Swiss knife for video processing. It encodes and decodes various video formats and supports some basic video processing, such as de-interlacing. To extract the audio track from the source, type:
ffmpeg -i <input_file> -vn <output_file>
The command can be applied to both DV/DivX/XviD AVI and MPEG files. The vn switch disables video in the output file. The resulting file would be a raw PCM audio file.
To generate an MPEG-4 complaint clip, you need MPEG-4 AAC audio. The MPEG4IP suite includes a redistributed AAC encoder called FAAC. At the of this writing, FAAD2 is available on SourceForge and uses the version 1.1 library for encoding, which is a bit faster. If you are interested, you can grab the source from faac.sourceforge.net. A copy of the FAAC binary should have been installed properly when you were installing the MPEG4IP suite.
To encode the raw PCM audio track split by FFmpeg, type:
faac -m4 -b64 -r48000 -pLC <input_file> <output_file>
The -m flag specifies the AAC MPEG version. We are creating MPEG-4 AAC so we use -m4. The -b flag specifies the bit rate for the encoded output. A value of 32 or 64 produces satisfactory quality and is an economical size for streaming. The -r flag specifies the sampling rate of the input file; otherwise, FAAC would not read the file. Instead, it would produce an error notifying the user that the file format is not supported. The last -p flag, which specifies the profile, is a bit more complicated. The Main profile includes all the coding tools (an MPEG term understood as "features"). The LC profile, which stands for low complexity, reduces decoding complexity on the client side (for slow devices or machines). The LTP profile, which stands for long term prediction, provides significant improvement in quality but also increases decoding complexity. It is best used for audio tracks with clear pitch. I use LC most of the time for my school's MPEG-4 clips.
MPEG4IP suite comes with two encoders, mp4encode and xvidenc. mp4encode encodes an AVI file to an MPEG-4 video clip with its built-in OpenDivX encoder or ISO MPEG-4 encoder, if specified. xvidenc, on the other hand, encodes raw video file with the XviD encoder. If you encode with these utilities, the input AVI file must contain a video track in raw YV12 (YUV12) format, and the audio track must be in raw PCM format. In this article, instead, I show how we can use FFmpeg to simplify the video encoding process. Because FFmpeg decodes DV, MPEG-1 and 2, DivX and XviD, we can skip the step of preparing YV12 raw for mp4encode or xvidenc. The command for encoding from these formats to ISO MPEG-4 video is the same:
ffmpeg -i <input_file> -an -b 300 -vcodec mpeg4 <output_file>
FFmpeg then encodes the input file without audio (the -an flag) at 300 kilobits/second, using the ISO MPEG-4 encoder to an AVI video file containing a single MPEG-4 video track. If you want to perform inverse telecine (IVTC) for NTSC source under Linux, you would need transcode, another nice program suite that provides useful video processing functionalities. It also is possible to encode the video in 2-pass mode to get the best result.
ffmpeg -i <input_file> -an -pass 1 -passlogfile <log_file> -qscale 2 -vcodec mpeg4 <output_file>
ffmpeg -i <input_file> -an -pass 2 -passlogfile <log_file> -b 300 -vcodec mpeg4 <output_file>
The input file, the output file and the log file in both passes must be the same. Also, you should specify your desired bit rate during the second pass instead of the first.
After encoding the audio and video, it is time to combine them to create a real MPEG-4 clip. The MPEG4IP suite provides a nice tool called mp4creator for this purpose. It can add or remove tracks in an MPEG-4 file. But, let's first create the MPEG-4 clip by adding a video track:
mp4creator -c myvideo.avi -hint mytest.mp4
The -hint flag tells mp4creator to add an additional hint track for the video track. Hinting is required if you are streaming a clip with Darwin Streaming Server. If the mytest.mp4 file does not exist already, mp4creator creates it for you. To add an audio track, enter:
mp4creator -c myaudio.aac -hint -interleave mytest.mp4
Both commands perform a similar action. The second command introduced the -interleave flag, which creates an interleaved RTP payload format for the audio hint track. If you are using MP3 for your audio track (possibly not), ignore this flag as it supports only AAC. Finally, optimize the clip:
mp4creator -optimize mytest.mp4
This command optimizes the file layout, hence improving its speed during streaming. The rearranged MPEG-4 file contains control information at the beginning of the file, thereby enabling HTTP streaming of the file. To see a list of tracks in an MPEG-4 file, use:
mp4creator -list mytest.mp4
If you have a successful MPEG-4 clip, the list should look something like this (a clip currently being streamed at my school):
MPEG-4 Simple @ L3, 30.030 secs, 299 kbps, 352x240 @ 29.97 fps
Payload MP4V-ES for track 1
MPEG-4, 29.973 secs, 65 kbps, 48000 Hz
Payload mpeg4-generic for track 5
Before putting the clip up to the streaming server, you should test it. The MPEG4IP suite comes with mp4player and gmp4player for playing locally stored or streamed MPEG-4 files. You should use gmp4player, as the console player provides little control of video playback. If everything looks fine, upload the MPEG-4 file to your streaming server's media directory. Hurray! Your video is ready to be streamed over the net!