bool CZipCentralDir::RemoveDataDescr(bool bFromBuffer) { ziparchv::CZipFileMapping fm; char* pFile; DWORD uSize; if (bFromBuffer) { uSize = m_pStorage->m_uBytesInWriteBuffer; pFile = m_pStorage->m_pWriteBuffer; } else { uSize = m_pStorage->m_pFile->GetLength(); // we cannot use CZipMemFile in multidisk archive // so it MUST be CZipFile if (!fm.CreateMapping(static_cast<CZipFile*>(m_pStorage->m_pFile))) return false; pFile = fm.GetMappedMemory(); } DWORD uOffsetToChange = 4; DWORD uPosInBuffer = 0; DWORD uExtraHeaderLen; int iCount = m_headers.GetSize(); for (int i = 0; i < iCount; i++) { // update the flag value in the local and central header // int uDataDescr = (m_headers[i]->m_uFlag & 8) ? (4 + 12) : 0; CZipFileHeader* pHeader = m_headers[i]; char* pSour = pFile + pHeader->m_uOffset; if (!pHeader->IsEncrypted()) { // removing data descriptor pHeader->m_uFlag &= ~8; // update local header: // write modified flag in the local header memcpy(pSour + 6, &pHeader->m_uFlag, 2); uExtraHeaderLen = 4/*ext. header signature*/ + 12/*data descriptor*/; } else // do not remove data descriptors from encrypted files uExtraHeaderLen = 0; // update crc32 and sizes' values pHeader->GetCrcAndSizes(pSour+ 14); DWORD uToCopy = (i == (iCount - 1) ? uSize : m_headers[i + 1]->m_uOffset) - pHeader->m_uOffset - uExtraHeaderLen; memmove(pFile + uPosInBuffer, pSour, uToCopy); uPosInBuffer += uToCopy; pHeader->m_uOffset -= uOffsetToChange; uOffsetToChange += uExtraHeaderLen; } if (bFromBuffer) m_pStorage->m_uBytesInWriteBuffer = uPosInBuffer; else { m_pStorage->m_iBytesWritten = uPosInBuffer; fm.RemoveMapping(); m_pStorage->m_pFile->SetLength(uPosInBuffer); } return true; }