mirror of
https://github.com/taglib/taglib.git
synced 2025-05-27 13:10:26 -04:00
Tolerate trailing garbage in M4A files (#1186)
If an M4A file contains trailing garbage (e.g. an APE tag at the
end of the file), it was considered invalid since [e21640b
].
It is important to make sure that atoms which affect modifications
written by TagLib are valid, otherwise the file might be damaged.
However, in cases where invalid atoms do not affect modifications
(which are only done inside the root level "moov" and "moof"
containers), they can be safely ignored.
This commit allows trailing garbage in M4A files as it is also
accepted in MP3, WAV and DSF files.
This commit is contained in:
parent
8b3f1a459e
commit
491322d1ba
@ -40,6 +40,35 @@ namespace
|
||||
return std::none_of(list.begin(), list.end(),
|
||||
[](const auto &a) { return a->length == 0 || !checkValid(a->children); });
|
||||
}
|
||||
|
||||
bool checkRootLevelAtoms(MP4::AtomList &list)
|
||||
{
|
||||
bool moovValid = false;
|
||||
for(auto it = list.begin(); it != list.end(); ++it) {
|
||||
bool invalid = (*it)->length == 0 || !checkValid((*it)->children);
|
||||
if(!moovValid && !invalid && (*it)->name == "moov") {
|
||||
moovValid = true;
|
||||
}
|
||||
if(invalid) {
|
||||
if(moovValid && (*it)->name != "moof") {
|
||||
// Only the root level atoms "moov" and (if present) "moof" are
|
||||
// modified. If they are valid, ignore following invalid root level
|
||||
// atoms as trailing garbage.
|
||||
while(it != list.end()) {
|
||||
delete *it;
|
||||
it = list.erase(it);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
class MP4::File::FilePrivate
|
||||
@ -127,7 +156,7 @@ MP4::File::read(bool readProperties)
|
||||
return;
|
||||
|
||||
d->atoms = std::make_unique<Atoms>(this);
|
||||
if(!checkValid(d->atoms->atoms)) {
|
||||
if(!checkRootLevelAtoms(d->atoms->atoms)) {
|
||||
setValid(false);
|
||||
return;
|
||||
}
|
||||
|
@ -602,10 +602,7 @@ public:
|
||||
void testFuzzedFile()
|
||||
{
|
||||
MP4::File f(TEST_FILE_PATH_C("infloop.m4a"));
|
||||
// The file has an invalid atom length of 2775 in the last atom
|
||||
// ("free", offset 0xc521, 00000ad7 66726565), whereas the remaining file
|
||||
// length is 2727 bytes, therefore the file is now considered invalid.
|
||||
CPPUNIT_ASSERT(!f.isValid());
|
||||
CPPUNIT_ASSERT(f.isValid());
|
||||
}
|
||||
|
||||
void testRepeatedSave()
|
||||
|
Loading…
Reference in New Issue
Block a user