Determine whether an audio file is encoded in Apple Lossless (ALAC) - audio

There are a number of audio files that have .m4a suffix and these are encoded in one of AAC or Apple Lossless (ALAC). I want to choose only audio files encoded in Apple Lossless of them. Is there any way to determine this? I tried FFmpeg, but it says all of them are encoded in AAC.
Edit: I am currently on Windows.

If you have the FFmpeg package, you should have ffprobe.
Give this a try:
ffprobe -v error -select_streams a:0 -show_entries stream=codec_name -of default=noprint_wrappers=1:nokey=1 file.m4a
-v error: to hide the startup text
-select_streams a:0: to select the first audio track
-show_entries stream=codec_name: to display only the codec type
-of default=noprint_wrappers=1:nokey=1: to remove extra formatting
This will print out just aac or alac. Perfect for scripting.

Here is a file that has a description of M4A (best I could find so far) on page 67:
http://iweb.dl.sourceforge.net/project/audiotools/audio%20formats%20reference/2.14/audioformats_2.14_letter.pdf
A typical M4A begins with an 'ftyp' atom indicating its file type...
10.2.1 the ftyp atom
[0 31] ftyp Length [32 63] 'ftyp' (0x66747970)
[64 95] Major Brand [96 127] Major Brand Version
[128 159] Compatible Brandā‚ ...
The 'Major Brand' and 'Compatible Brand' elds are ASCII strings.
'Major Brand Version' is an integer.
At first I figured 'ftyp' would be where format is determined, but judging by this list that is more like the file type itself (already known as m4a):
http://www.ftyps.com/index.html
http://www.ftyps.com/what.html Describes a bit more of the format.
If ftyp doesn't differentiate, then I think that the 'Major Brand' field might refer to the fourcc's on this page:
http://wiki.multimedia.cx/index.php?title=QuickTime_container
The one for Apple Lossless being 'alac' and AAC is probably 'mp4a'
Apple's Lossless format open source page indicates that the ftype is 'alac' (slightly contradictory to above)
http://alac.macosforge.org/trac/browser/trunk/ALACMagicCookieDescription.txt
So far what I can tell is that the 4 bytes following ftyp are always (in a smallish sample size) 'M4A '.
Somewhere in the first ~200 (hex) bytes or so there is an ascii 'mp4a' for AAC compression or an 'alac' for Apple Lossless. The 'alac' always seems to come in pairs ~30 bytes apart ('mp4a' only once).
Sorry that's not more specific, if I find the exact location or prefix I'll update again. (My guess is the earlier part of the header has a size specified somewhere.)

You can do it with Core Audio.
Something like:
CFStringRef pathToFile;
CFURLRef inputFileURL = CFURLCreateWithFileSystemPath(kCFAllocatorDefault, pathToFile, kCFURLPOSIXPathStyle, false);
ExtAudioFileRef inputFile;
ExtAudioFileOpenURL(inputFileURL, &inputFile);
AudioStreamBasicDescription fileDescription;
UInt32 propertySize = sizeof(fileDescription);
ExtAudioFileGetProperty(inputFile,
kExtAudioFileProperty_FileDataFormat,
&propertySize,
&fileDescription);
if(fileDescription.mFormatID == kAudioFormatAppleLossless){
// file is apple lossless
}

On a Mac, you select the file you want and then right click. Find "Get Info" and click that and a window will pop up with extra information about the file you selected. It should say next to "Codecs:" "AAC" or "Apple Lossless"
I hope I helped those Mac users out there that had the same question (and possibly Windows users in some way even though I am not familiar with the OS.)

try using http://sourceforge.net/projects/mediainfo/
"MediaInfo is a convenient unified display of the most relevant technical and tag data for video and audio files." - sourceforge project description
This is how info is displayed.
General
Complete name : C:\Downloads\recit24bit.m4a
Format : MPEG-4
Format profile : Apple audio with iTunes info
Codec ID : M4A
File size : 2.62 MiB
Duration : 9s 9ms
Overall bit rate : 2 441 Kbps
Track name : 24 bit recital ALAC Test File
Performer : N\A
Comment : Test File
Audio
ID : 1
Format : ALAC
Codec ID : alac
Codec ID/Info : Apple Lossless Format
Duration : 9s 9ms
Bit rate mode : Variable
Bit rate : 2 438 Kbps
Channel(s) : 2 channels
Sampling rate : 22.7 KHz
Bit depth : 24 bits
Stream size : 2.62 MiB (100%)
Language : English
Check audio section for codec/encoding details.

Related

How to make Safari play local audio resource?

This is macOS / Safari.
I can play this file by opening in Safari: https://learnwithecho.com/assets/test.m4a
But if I save that file locally:
wget https://learnwithecho.com/assets/test.m4a
And spin up a web server:
php -S 0.0.0.0:8888
And load the same file locally:
open http://localhost:8888/test.m4a
Then I get this error:
Failed to load resource: Plug-in handled load
How can I serve this file locally so it properly plays in Safari?
Here is mediainfo for the file:
General
Complete name : assets/test.m4a
Format : MPEG-4
Format profile : Apple audio with iTunes info
Codec ID : M4A (isom/iso2)
File size : 26.3 KiB
Duration : 2 s 24 ms
Overall bit rate mode : Constant
Overall bit rate : 106 kb/s
Writing application : Lavf55.33.100
Audio
ID : 1
Format : AAC LC
Format/Info : Advanced Audio Codec Low Complexity
Codec ID : mp4a-40-2
Duration : 2 s 24 ms
Duration_LastFrame : -20 ms
Bit rate mode : Constant
Bit rate : 102 kb/s
Channel(s) : 1 channel
Channel layout : C
Sampling rate : 44.1 kHz
Frame rate : 43.066 FPS (1024 SPF)
Compression mode : Lossy
Stream size : 25.2 KiB (96%)
Default : Yes
Alternate group : 1
Okay, this is the dumbest thing I found out.
macOS / Safari (at least version 13.0.3) does not support playing media resources on localhost using RELATIVE URLs.
The same media WILL play if you use an ABSOLUTE URL like http://localhost...
This is undocumented Safari behavior.

Creating M4A file from MP4

I want to create an M4A file from an MP4, I want to attempt this from scratch without using other libraries but just the raw data.
So far I am able to locate the atom moov and parser it. And as a result I can pull the audio data from the mdat. So then I create my own M4A file with the right ftyp (M4A isomiso2) then add a new mdat with just the audio data I previously recovered, finally I add the moov with the same mvhd, and only the audio trak but with an updated stco to reflect the change in offsets of the chunks of audio data (as they are just one after each other now). I am sure I am doing all of this right.
However the M4A file just plays silence. I believe it is because I have to edit more in the moov but I am not sure what - I put it into FFmpeg corruption and I got:
"Sample rate index in program config element does not match the sample rate index configured by the container."
"Too large remapped id is not implemented."
So as a result I think it is something to do with the stsd atom but I am not sure how to change it.

HandbrakeCLI command lines

I'm trying to convert DVD iso files to mp4 using HandbrakeCLI. I use the following line in a batch file:
D:\HandBrakeCLI.exe -i "D:\input.iso" -o "D:\output.mp4" --no-markers --width "720" --height "480" --preset "HQ 480p30 Surround" --encoder "mpeg2" --audio-lang-list "eng"
When I do this, I must then extract the audio from the file, using the following line:
D:\eac3to\eac3to.exe "D:\output.mp4" "D:\output.wavs" -down16
However, when I attempt to extract the audio, I get the error message
The format of the source file could not be detected.
Is there anything wrong with my former line of code that's causing the mp4 to get screwed up?
Minor side question: I'm also trying to get handbrake to remove subtitles and also only keep English audio, do you know what code could be used for that? I started a bit there with the --audio-lang-list "eng" but I'm now sure what to do from there.
Thanks a lot in advance!
You need to use a valid audio format. .wavs is not valid. You have to use an available audio codec to output to the below for --aencoder. The default output audio for MP4 is .aac
av_aac
copy:aac
ac3
copy:ac3
eac3
copy:eac3
copy:truehd
copy:dts
copy:dtshd
mp3
copy:mp3
vorbis
flac16
flac24
copy:flac
opus
copy
Defaults for audio
av_mp4 = av_aac
av_mkv = mp3
You need to pass none for no subtitles
-s none
And define only eng track like you were doing
--audio-lang-list eng
Check out the Handbrake CLI Documentation for the command line code:
https://handbrake.fr/docs/en/latest/cli/cli-guide.html
You can also try using a different program once you extract the audio. A program like XMediaRecode. It can also remux audio and video and convert other audio formats to wav
https://www.videohelp.com/software/XMedia-Recode

How to detect if a file is encoded using mp3PRO?

I have a folder which contains lot of MP3 files, some of them are encoded using mp3PRO.
Since this format is now obsolete, I'd like to convert them back to MP3 (converters can be found easily).
Is there is a way to detect programatically if a file is encoded using mp3PRO format ? (eg : by looking at file header or specific signatures using an hex editor)
The official player is able to detect if file is encoded using mp3PRO (the logo is highlighted or not) so I suppose this is technically possible.
What I found so far is that bitrate of mp3PRO file appears to be pretty low (50% of non encoded file) : eg : a 128 kbps file will appears as 64kbps. However a 320 kbps file will appears as 160 kpbs (which are pretty common) so it cannot be used as a rule.
Here is what I found out and how I fixed it. I wrote in here in case somebody would need it :
MP3Pro files does not contains any special flag in the mp3 header that would help to recognize them.
They are technically very similar to usual mp3 files, except they are encoded half the bit and sample rate (eg : a 128kpbs 44100hz file will be encoded as a 64kps 22050hz file, resulting in mp3pro file being approx half the size of original file).
This has been made for compatibility, so default players can play them without any change.
They also contains some SBR data, which allow to synthetically rebuild the lost audio part (high frequencies) and to play them it was before the mp3 pro conversion.
Detecting the SBR data seems very hard if not impossible : it would require to decode the actual mp3 frames. Also there is no documentation to be found about mp3pro format.
What I did (which works but required some manual effort) : I added all files to be checked to playlist of an mp3 player (foobar 2000 in my case) then sorted the files on the sample rate column : most 22050 hz mp3 files were indeed mp3 pro files.
They were converted back to mp3 using winamp + the mp3pro plugin made for it, available here : http://www.wav-mp3.com/mp3pro-to-mp3.htm

Beaglebone Black Video Capture: Error "select timeout"

Hey I'm following Derek Molloy's tutorial:
http://derekmolloy.ie/beaglebone/beaglebone-video-capture-and-image-processing-on-embedded-linux-using-opencv/#comment-30209
Using a Logitech c310 webcam, that is supported by the Linux UVC drivers.
root#beaglebone:/boneCV# v4l2-ctl --all
Driver Info (not using libv4l2):
Driver name : uvcvideo
Card type : UVC Camera (046d:081b)
Bus info : usb-musb-hdrc.1.auto-1
Driver version: 3.8.13
Capabilities : 0x84000001
Video Capture
Streaming
Format Video Capture:
Width/Height : 640/480
Pixel Format : 'YUYV'
Field : None
Bytes per Line: 1280
Size Image : 614400
Colorspace : SRGB
Crop Capability Video Capture:
Bounds : Left 0, Top 0, Width 640, Height 480
Default : Left 0, Top 0, Width 640, Height 480
Pixel Aspect: 1/1
Video input : 0 (Camera 1: ok)
Streaming Parameters Video Capture:
Capabilities : timeperframe
Frames per second: 30.000 (30/1)
Read buffers : 0
Priority: 2
So we can see it is read by the Beagleboard no problem.
When I try to capture the video, I simply get this error:
root#beaglebone:/boneCV# ./capture -f -c 600 -o > output.raw
Force Format 1
select timeout
Looking at other threads, people don't seem to know how to answer this question, can anyone with experience on this project help me out?
If you compare the image size of YUYV and that of MJPEG you will notice that the former is much larger than the latter. BBB has limited bandwidth on its USB port so thats why you cannot operate your camera in YUYV format. MJPEG outputs compressed video stream. Different opencv versions tend to change the resolution that you set with v4l2-ctl command so you have to change the resolution in the boneCV code. I'm not sure how its done in c++ but in python, check Changing camera resolution in opencv code. According to Matthew, Bandwidth limitations he tested and found out the bandwidth to be 13.2MB/s.
Well I can say the issue is resolved. After rebooting and trying the camera again after several hours, it magically seems to work.
The only thing I changed is the capture call to be simpler it is now:
./capture -o > output.raw
I haven't converted the raw file to mpeg4 yet, since I'm installing ffmpeg as I type this, however I can confirm that grabbing still images is working. The filesize of the output.raw is confirmation that it is indeed capturing video as well. If anyone finds this and is stuck, I will be glad to give assistance as much as I can.
Strangely, it only seems to capture video after using the picture grabber program first. So there must be something the grabber is initializing that isn't happening in the capture.
UPDATE: Ok it turns out that the YUYV video mode is not working but the mjpeg does, putting it into grabber mode initialized mjpeg mode and that's why it worked. Not sure why YUYV doesn't work yet.

Resources