## Summary 7-Zip supports extracting from [Compound Documents](https://en.wikipedia.org/wiki/Compound_document). Null pointer dereference in the Compound handler may lead to denial of service.
## Tested Version [7-Zip 24.09](https://sourceforge.net/p/sevenzip/discussion/45797/thread/b95432c7ac/) ## Details ### Null pointer array write attempt in `NArchive::NCom::CHandler::GetStream` When `item.Size` is a certain large number `(item.Size + clusterSize - 1) >> bsLog` at [1] may overflow and `numClusters64` becomes zero. Note that `if (numClusters64 >= ((UInt32)1 << 31))` check at [2] doesn't prevent the unsigned integer overflow. Then the vector call `ClearAndReserve` at [3] doesn't allocate any memory and the internal vector pointer stays `null`. This leads to a null pointer write attempt at [4]. ```cpp Z7_COM7F_IMF(CHandler::GetStream(UInt32 index, ISequentialInStream **stream)) { ... const UInt64 numClusters64 = (item.Size + clusterSize - 1) >> bsLog; // <----- 1 if (numClusters64 >= ((UInt32)1 << 31)) // <----- 2 return E_NOTIMPL; streamSpec->Vector.ClearAndReserve((unsigned)numClusters64); // <----- 3 UInt32 sid = item.Sid; UInt64 size = item.Size; if (size != 0) { for (;; size -= clusterSize) { if (isLargeStream) { if (sid >= _db.FatSize) return S_FALSE; streamSpec->Vector.AddInReserved(sid + 1); // <----- 4 ``` A PoC triggers null pointer write dereference when `7zz` is compiled with ASAN and extracted, for example as `7zz e -so compound-crash.poc`: ``` ==2387581==ERROR: AddressSanitizer: SEGV on unknown address 0x000000000000 (pc 0x5615317c0993 bp 0x7ffcb31a1350 sp 0x7ffcb31a1300 T0) ==2387581==The signal is caused by a WRITE memory access. ==2387581==Hint: address points to the zero page. #0 0x5615317c0993 in CRecordVector<unsigned int>::AddInReserved(unsigned int) ../../Archive/../../Common/MyVector.h:249:18 #1 0x5615317bfe66 in NArchive::NCom::CHandler::GetStream(unsigned int, ISequentialInStream**) /src/7-zip/CPP/7zip/Bundles/Alone2/../../Archive/ComHandler.cpp:866:28 #2 0x5615317bea3d in NArchive::NCom::CHandler::Extract(unsigned int const*, unsigned int, int, IArchiveExtractCallback*) /src/7-zip/CPP/7zip/Bundles/Alone2/../../Archive/ComHandler.cpp:806:20 #3 0x561531e94bbb in DecompressArchive(CCodecs*, CArchiveLink const&, unsigned long, NWildcard::CCensorNode const&, CExtractOptions const&, bool, IExtractCallbackUI*, IFolderArchiveExtractCallback*, CArchiveExtractCallback*, UString&, unsigned long&) /src/7-zip/CPP/7zip/Bundles/Alone2/../../UI/Common/Extract.cpp:235:23 #4 0x561531e8fdf1 in Extract(CCodecs*, CObjectVector<COpenType> const&, CRecordVector<int> const&, CObjectVector<UString>&, CObjectVector<UString>&, NWildcard::CCensorNode const&, CExtractOptions const&, IOpenCallbackUI*, IExtractCallbackUI*, IFolderArchiveExtractCallback*, IHashCalc*, UString&, CDecompressStat&) /src/7-zip/CPP/7zip/Bundles/Alone2/../../UI/Common/Extract.cpp:542:5 #5 0x561531f49d3a in Main2(int, char**) /src/7-zip/CPP/7zip/Bundles/Alone2/../../UI/Console/Main.cpp:1378:21 #6 0x561531f55ae4 in main /src/7-zip/CPP/7zip/Bundles/Alone2/../../UI/Console/MainAr.cpp:162:11 ``` On Windows the same PoC was tested to crash the official 7-Zip build even without ASAN. #### Impact This issue may lead to denial of service. ## Credit This issue was discovered and reported by GHSL team member [@JarLob (Jaroslav Lobačevski)](https://github.com/JarLob). ## Coordinated Disclosure Timeline - 2025-04-24: Reported as a private issue - 2025-04-29: Report acknowledged - 2025-07-05: Fixed in v25.00