diff options
author | Max Kellermann <max@duempel.org> | 2016-03-07 14:18:39 +0100 |
---|---|---|
committer | Max Kellermann <max@duempel.org> | 2016-03-07 14:21:01 +0100 |
commit | e140a28073f75375a33b28bcbcd0ecc669c5a518 (patch) | |
tree | ebd7207c3192c42ed5a59288f65599132c043953 | |
parent | de61c3b9626d24685e58f880667001129e5b8921 (diff) |
archive/iso9660: check path buffer bounds
-rw-r--r-- | NEWS | 2 | ||||
-rw-r--r-- | src/archive/plugins/Iso9660ArchivePlugin.cxx | 15 |
2 files changed, 13 insertions, 4 deletions
@@ -2,6 +2,8 @@ ver 0.19.14 (not yet released) * decoder - dsdiff: fix off-by-one buffer overflow - opus: limit tag size to 64 kB +* archive + - iso9660: fix buffer overflow * fix build failures on non-glibc builds due to constexpr Mutex ver 0.19.13 (2016/02/23) diff --git a/src/archive/plugins/Iso9660ArchivePlugin.cxx b/src/archive/plugins/Iso9660ArchivePlugin.cxx index 24609f1ed..6b5f47e86 100644 --- a/src/archive/plugins/Iso9660ArchivePlugin.cxx +++ b/src/archive/plugins/Iso9660ArchivePlugin.cxx @@ -66,7 +66,10 @@ public: return iso9660_iso_seek_read(iso, ptr, start, i_size); } - void Visit(char *path, size_t length, + /** + * @param capacity the path buffer size + */ + void Visit(char *path, size_t length, size_t capacity, ArchiveVisitor &visitor); virtual void Close() override { @@ -85,7 +88,7 @@ static constexpr Domain iso9660_domain("iso9660"); /* archive open && listing routine */ inline void -Iso9660ArchiveFile::Visit(char *path, size_t length, +Iso9660ArchiveFile::Visit(char *path, size_t length, size_t capacity, ArchiveVisitor &visitor) { auto *entlist = iso9660_ifs_readdir(iso, path); @@ -102,12 +105,16 @@ Iso9660ArchiveFile::Visit(char *path, size_t length, continue; size_t filename_length = strlen(filename); + if (length + filename_length + 1 >= capacity) + /* file name is too long */ + continue; + memcpy(path + length, filename, filename_length + 1); size_t new_length = length + filename_length; if (iso9660_stat_s::_STAT_DIR == statbuf->type ) { memcpy(path + new_length, "/", 2); - Visit(path, new_length + 1, visitor); + Visit(path, new_length + 1, capacity, visitor); } else { //remove leading / visitor.VisitArchiveEntry(path + 1); @@ -135,7 +142,7 @@ void Iso9660ArchiveFile::Visit(ArchiveVisitor &visitor) { char path[4096] = "/"; - Visit(path, 1, visitor); + Visit(path, 1, sizeof(path), visitor); } /* single archive handling */ |