1baa3858d3f5d128a5c8466b700098109edcad5f2repo sync// Update.cpp 2baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 3baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "StdAfx.h" 4baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 5baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "Update.h" 6baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 7cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Common/IntToString.h" 8cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Common/StringConvert.h" 9baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 10cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/DLL.h" 11cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/FileDir.h" 12cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/FileFind.h" 13cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/FileName.h" 14cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/PropVariant.h" 15cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/PropVariantConv.h" 16cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../../Windows/TimeUtils.h" 17baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 18baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../Common/FileStreams.h" 19cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include "../../Common/LimitedStreams.h" 20baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 21baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../Compress/CopyCoder.h" 22baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 23baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../Common/DirItem.h" 24baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../Common/EnumDirItems.h" 25baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../Common/OpenArchive.h" 26baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../Common/UpdateProduce.h" 27baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 28baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "EnumDirItems.h" 29baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "SetProperties.h" 30baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "TempFiles.h" 31baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "UpdateCallback.h" 32baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 33baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const char *kUpdateIsNotSupoorted = 34baa3858d3f5d128a5c8466b700098109edcad5f2repo sync "update operations are not supported for this archive"; 35baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 36baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NWindows; 37baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NCOM; 38baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NFile; 39cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckyusing namespace NDir; 40baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NName; 41baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 42cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic CFSTR kTempFolderPrefix = FTEXT("7zE"); 43cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 44cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 45cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic bool DeleteEmptyFolderAndEmptySubFolders(const FString &path) 46cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 47cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NFind::CFileInfo fileInfo; 48cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString pathPrefix = path + FCHAR_PATH_SEPARATOR; 49cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 50cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NFind::CEnumerator enumerator(pathPrefix + FCHAR_ANY_MASK); 51cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky while (enumerator.Next(fileInfo)) 52cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 53cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (fileInfo.IsDir()) 54cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!DeleteEmptyFolderAndEmptySubFolders(pathPrefix + fileInfo.Name)) 55cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 56cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 57cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 58cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 59cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // we don't need clear read-only for folders 60cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!MySetFileAttributes(path, 0)) 61cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 62cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 63cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return RemoveDir(path); 64cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 65cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 66baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 67baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NUpdateArchive; 68baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 69baa3858d3f5d128a5c8466b700098109edcad5f2repo syncclass COutMultiVolStream: 70baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public IOutStream, 71baa3858d3f5d128a5c8466b700098109edcad5f2repo sync public CMyUnknownImp 72baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 73cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned _streamIndex; // required stream 74baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 _offsetPos; // offset from start of _streamIndex index 75baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 _absPos; 76baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 _length; 77baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 78cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky struct CAltStreamInfo 79baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 80baa3858d3f5d128a5c8466b700098109edcad5f2repo sync COutFileStream *StreamSpec; 81baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<IOutStream> Stream; 82cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString Name; 83baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 Pos; 84baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 RealSize; 85baa3858d3f5d128a5c8466b700098109edcad5f2repo sync }; 86cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CObjectVector<CAltStreamInfo> Streams; 87baa3858d3f5d128a5c8466b700098109edcad5f2repo syncpublic: 88baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // CMyComPtr<IArchiveUpdateCallback2> VolumeCallback; 89baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CRecordVector<UInt64> Sizes; 90cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString Prefix; 91baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CTempFiles *TempFiles; 92baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 93baa3858d3f5d128a5c8466b700098109edcad5f2repo sync void Init() 94baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 95baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _streamIndex = 0; 96baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos = 0; 97baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _absPos = 0; 98baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _length = 0; 99baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 100baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 101cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool SetMTime(const FILETIME *mTime); 102baa3858d3f5d128a5c8466b700098109edcad5f2repo sync HRESULT Close(); 103baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 104baa3858d3f5d128a5c8466b700098109edcad5f2repo sync MY_UNKNOWN_IMP1(IOutStream) 105baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 106baa3858d3f5d128a5c8466b700098109edcad5f2repo sync STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize); 107baa3858d3f5d128a5c8466b700098109edcad5f2repo sync STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition); 108baa3858d3f5d128a5c8466b700098109edcad5f2repo sync STDMETHOD(SetSize)(UInt64 newSize); 109baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}; 110baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 111baa3858d3f5d128a5c8466b700098109edcad5f2repo sync// static NSynchronization::CCriticalSection g_TempPathsCS; 112baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 113baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT COutMultiVolStream::Close() 114baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 115baa3858d3f5d128a5c8466b700098109edcad5f2repo sync HRESULT res = S_OK; 116cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, Streams) 117baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 118cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky COutFileStream *s = Streams[i].StreamSpec; 119cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (s) 120baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 121cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky HRESULT res2 = s->Close(); 122baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (res2 != S_OK) 123baa3858d3f5d128a5c8466b700098109edcad5f2repo sync res = res2; 124baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 125baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 126baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return res; 127baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 128baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 129cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckybool COutMultiVolStream::SetMTime(const FILETIME *mTime) 130cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 131cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool res = true; 132cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, Streams) 133cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 134cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky COutFileStream *s = Streams[i].StreamSpec; 135cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (s) 136cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!s->SetMTime(mTime)) 137cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky res = false; 138cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 139cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return res; 140cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 141cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 142baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *processedSize) 143baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 144baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (processedSize != NULL) 145baa3858d3f5d128a5c8466b700098109edcad5f2repo sync *processedSize = 0; 146cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky while (size > 0) 147baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 148baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (_streamIndex >= Streams.Size()) 149baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 150cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CAltStreamInfo altStream; 151baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 152cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FChar temp[16]; 153baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ConvertUInt32ToString(_streamIndex + 1, temp); 154cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString res = temp; 155cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky while (res.Len() < 3) 156cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky res = FString(FTEXT('0')) + res; 157cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString name = Prefix + res; 158cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.StreamSpec = new COutFileStream; 159cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Stream = altStream.StreamSpec; 160cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!altStream.StreamSpec->Create(name, false)) 161baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return ::GetLastError(); 162baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 163baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // NSynchronization::CCriticalSectionLock lock(g_TempPathsCS); 164baa3858d3f5d128a5c8466b700098109edcad5f2repo sync TempFiles->Paths.Add(name); 165baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 166baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 167cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Pos = 0; 168cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.RealSize = 0; 169cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Name = name; 170cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky Streams.Add(altStream); 171baa3858d3f5d128a5c8466b700098109edcad5f2repo sync continue; 172baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 173cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CAltStreamInfo &altStream = Streams[_streamIndex]; 174baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 175cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned index = _streamIndex; 176baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (index >= Sizes.Size()) 177baa3858d3f5d128a5c8466b700098109edcad5f2repo sync index = Sizes.Size() - 1; 178baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt64 volSize = Sizes[index]; 179baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 180baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (_offsetPos >= volSize) 181baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 182baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos -= volSize; 183baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _streamIndex++; 184baa3858d3f5d128a5c8466b700098109edcad5f2repo sync continue; 185baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 186cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (_offsetPos != altStream.Pos) 187baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 188baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // CMyComPtr<IOutStream> outStream; 189cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // RINOK(altStream.Stream.QueryInterface(IID_IOutStream, &outStream)); 190cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(altStream.Stream->Seek(_offsetPos, STREAM_SEEK_SET, NULL)); 191cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Pos = _offsetPos; 192baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 193baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 194cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UInt32 curSize = (UInt32)MyMin((UInt64)size, volSize - altStream.Pos); 195baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt32 realProcessed; 196cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(altStream.Stream->Write(data, curSize, &realProcessed)); 197baa3858d3f5d128a5c8466b700098109edcad5f2repo sync data = (void *)((Byte *)data + realProcessed); 198baa3858d3f5d128a5c8466b700098109edcad5f2repo sync size -= realProcessed; 199cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Pos += realProcessed; 200baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos += realProcessed; 201baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _absPos += realProcessed; 202baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (_absPos > _length) 203baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _length = _absPos; 204cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (_offsetPos > altStream.RealSize) 205cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.RealSize = _offsetPos; 206baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (processedSize != NULL) 207baa3858d3f5d128a5c8466b700098109edcad5f2repo sync *processedSize += realProcessed; 208cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (altStream.Pos == volSize) 209baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 210baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _streamIndex++; 211baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos = 0; 212baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 213baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (realProcessed == 0 && curSize != 0) 214baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 215baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 216baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 217baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return S_OK; 218baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 219baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 220baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP COutMultiVolStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition) 221baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 222baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (seekOrigin >= 3) 223baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return STG_E_INVALIDFUNCTION; 224cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky switch (seekOrigin) 225baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 226cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky case STREAM_SEEK_SET: _absPos = offset; break; 227cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky case STREAM_SEEK_CUR: _absPos += offset; break; 228cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky case STREAM_SEEK_END: _absPos = _length + offset; break; 229baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 230baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos = _absPos; 231baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (newPosition != NULL) 232baa3858d3f5d128a5c8466b700098109edcad5f2repo sync *newPosition = _absPos; 233baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _streamIndex = 0; 234baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return S_OK; 235baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 236baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 237baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP COutMultiVolStream::SetSize(UInt64 newSize) 238baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 239baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (newSize < 0) 240baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_INVALIDARG; 241cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned i = 0; 242baa3858d3f5d128a5c8466b700098109edcad5f2repo sync while (i < Streams.Size()) 243baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 244cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CAltStreamInfo &altStream = Streams[i++]; 245cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if ((UInt64)newSize < altStream.RealSize) 246baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 247cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(altStream.Stream->SetSize(newSize)); 248cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.RealSize = newSize; 249baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 250baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 251cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky newSize -= altStream.RealSize; 252baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 253baa3858d3f5d128a5c8466b700098109edcad5f2repo sync while (i < Streams.Size()) 254baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 255baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 256cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CAltStreamInfo &altStream = Streams.Back(); 257cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky altStream.Stream.Release(); 258cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky DeleteFileAlways(altStream.Name); 259baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 260baa3858d3f5d128a5c8466b700098109edcad5f2repo sync Streams.DeleteBack(); 261baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 262baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _offsetPos = _absPos; 263baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _streamIndex = 0; 264baa3858d3f5d128a5c8466b700098109edcad5f2repo sync _length = newSize; 265baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return S_OK; 266baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 267baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 268cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckyvoid CArchivePath::ParseFromPath(const UString &path, EArcNameMode mode) 269cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 270cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky OriginalPath = path; 271cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 272cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky SplitPathToParts_2(path, Prefix, Name); 273cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 274cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (mode == k_ArcNameMode_Add) 275cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return; 276cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (mode == k_ArcNameMode_Exact) 277cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 278cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky BaseExtension.Empty(); 279cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return; 280cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 281cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 282cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int dotPos = Name.ReverseFind(L'.'); 283cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (dotPos < 0) 284cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return; 285cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if ((unsigned)dotPos == Name.Len() - 1) 286cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 287cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky Name.DeleteBack(); 288cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky BaseExtension.Empty(); 289cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return; 290cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 291cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const UString ext = Name.Ptr(dotPos + 1); 292cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (BaseExtension.IsEqualToNoCase(ext)) 293cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 294cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky BaseExtension = ext; 295cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky Name.DeleteFrom(dotPos); 296cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 297cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 298cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky BaseExtension.Empty(); 299cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 300cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 301cd66d540cead3f8200b0c73bad9c276d67896c3dDavid SrbeckyUString CArchivePath::GetFinalPath() const 302cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 303cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString path = GetPathWithoutExt(); 304cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!BaseExtension.IsEmpty()) 305cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky path += UString(L'.') + BaseExtension; 306cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return path; 307cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 308cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 309cd66d540cead3f8200b0c73bad9c276d67896c3dDavid SrbeckyUString CArchivePath::GetFinalVolPath() const 310cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 311cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString path = GetPathWithoutExt(); 312cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!BaseExtension.IsEmpty()) 313cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky path += UString(L'.') + VolExtension; 314cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return path; 315cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 316cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 317cd66d540cead3f8200b0c73bad9c276d67896c3dDavid SrbeckyFString CArchivePath::GetTempPath() const 318cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 319cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString path = TempPrefix + us2fs(Name); 320cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!BaseExtension.IsEmpty()) 321cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky path += FString(FTEXT('.')) + us2fs(BaseExtension); 322cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky path += FTEXT(".tmp"); 323cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky path += TempPostfix; 324cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return path; 325cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 326cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 327cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic const wchar_t *kDefaultArcType = L"7z"; 328cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic const wchar_t *kDefaultArcExt = L"7z"; 329baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const wchar_t *kSFXExtension = 330baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #ifdef _WIN32 331baa3858d3f5d128a5c8466b700098109edcad5f2repo sync L"exe"; 332baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #else 333baa3858d3f5d128a5c8466b700098109edcad5f2repo sync L""; 334baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #endif 335baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 336cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckybool CUpdateOptions::InitFormatIndex(const CCodecs *codecs, 337cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CObjectVector<COpenType> &types, const UString &arcPath) 338baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 339cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (types.Size() > 1) 340baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return false; 341cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // int arcTypeIndex = -1; 342cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (types.Size() != 0) 343cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 344cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MethodMode.Type = types[0]; 345cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MethodMode.Type_Defined = true; 346cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 347cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (MethodMode.Type.FormatIndex < 0) 348cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 349cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // MethodMode.Type = -1; 350cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MethodMode.Type = COpenType(); 351cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (ArcNameMode != k_ArcNameMode_Add) 352cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 353cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MethodMode.Type.FormatIndex = codecs->FindFormatForArchiveName(arcPath); 354cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (MethodMode.Type.FormatIndex >= 0) 355cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MethodMode.Type_Defined = true; 356cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 357cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 358cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return true; 359cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 360cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 361cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckybool CUpdateOptions::SetArcPath(const CCodecs *codecs, const UString &arcPath) 362cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 363cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString typeExt; 364cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int formatIndex = MethodMode.Type.FormatIndex; 365cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (formatIndex < 0) 366cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 367cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky typeExt = kDefaultArcExt; 368cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 369baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 370baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 371cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CArcInfoEx &arcInfo = codecs->Formats[formatIndex]; 372cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!arcInfo.UpdateEnabled) 373cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 374cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky typeExt = arcInfo.GetMainExt(); 375baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 376baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UString ext = typeExt; 377baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (SfxMode) 378baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ext = kSFXExtension; 379baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ArchivePath.BaseExtension = ext; 380baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ArchivePath.VolExtension = typeExt; 381cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ArchivePath.ParseFromPath(arcPath, ArcNameMode); 382cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, Commands) 383baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 384baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CUpdateArchiveCommand &uc = Commands[i]; 385baa3858d3f5d128a5c8466b700098109edcad5f2repo sync uc.ArchivePath.BaseExtension = ext; 386baa3858d3f5d128a5c8466b700098109edcad5f2repo sync uc.ArchivePath.VolExtension = typeExt; 387cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky uc.ArchivePath.ParseFromPath(uc.UserArchivePath, ArcNameMode); 388baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 389baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return true; 390baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 391baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 392baa3858d3f5d128a5c8466b700098109edcad5f2repo sync/* 393baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstruct CUpdateProduceCallbackImp: public IUpdateProduceCallback 394baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 395baa3858d3f5d128a5c8466b700098109edcad5f2repo sync const CObjectVector<CArcItem> *_arcItems; 396baa3858d3f5d128a5c8466b700098109edcad5f2repo sync IUpdateCallbackUI *_callback; 397baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 398baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CUpdateProduceCallbackImp(const CObjectVector<CArcItem> *a, 399baa3858d3f5d128a5c8466b700098109edcad5f2repo sync IUpdateCallbackUI *callback): _arcItems(a), _callback(callback) {} 400baa3858d3f5d128a5c8466b700098109edcad5f2repo sync virtual HRESULT ShowDeleteFile(int arcIndex); 401baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}; 402baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 403baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CUpdateProduceCallbackImp::ShowDeleteFile(int arcIndex) 404baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 405baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return _callback->ShowDeleteFile((*_arcItems)[arcIndex].Name); 406baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 407baa3858d3f5d128a5c8466b700098109edcad5f2repo sync*/ 408baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 409cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckybool CRenamePair::Prepare() 410cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 411cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (RecursedType != NRecursedType::kNonRecursed) 412cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 413cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!WildcardParsing) 414cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return true; 415cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return !DoesNameContainWildcard(OldName); 416cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 417cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 418cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckyextern bool g_CaseSensitive; 419cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 420cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic int CompareTwoNames(const wchar_t *s1, const wchar_t *s2) 421cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 422cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (int i = 0;; i++) 423cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 424cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky wchar_t c1 = s1[i]; 425cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky wchar_t c2 = s2[i]; 426cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (c1 == 0 || c2 == 0) 427cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return i; 428cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (c1 == c2) 429cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky continue; 430cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!g_CaseSensitive && (MyCharUpper(c1) == MyCharUpper(c2))) 431cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky continue; 432cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (IsCharDirLimiter(c1) && IsCharDirLimiter(c2)) 433cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky continue; 434cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return i; 435cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 436cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 437cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 438cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckybool CRenamePair::GetNewPath(bool isFolder, const UString &src, UString &dest) const 439cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 440cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int num = CompareTwoNames(OldName, src); 441cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (OldName[num] == 0) 442cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 443cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (src[num] != 0 && !IsCharDirLimiter(src[num]) && num != 0 && !IsCharDirLimiter(src[num - 1])) 444cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 445cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 446cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 447cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 448cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // OldName[num] != 0 449cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // OldName = "1\1a.txt" 450cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // src = "1" 451cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 452cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!isFolder || 453cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky src[num] != 0 || 454cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky !IsCharDirLimiter(OldName[num]) || 455cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky OldName[num + 1] != 0) 456cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return false; 457cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 458cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dest = NewName + src.Ptr(num); 459cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return true; 460cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 461cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 462cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic int GetReverseSlashPos(const UString &name) 463cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 464cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int slashPos = name.ReverseFind(L'/'); 465cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #ifdef _WIN32 466cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int slash1Pos = name.ReverseFind(L'\\'); 467cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky slashPos = MyMax(slashPos, slash1Pos); 468cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 469cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return slashPos; 470cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 471cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 472baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic HRESULT Compress( 473cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CUpdateOptions &options, 474baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CCodecs *codecs, 475baa3858d3f5d128a5c8466b700098109edcad5f2repo sync const CActionSet &actionSet, 476cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CArc *arc, 477baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchivePath &archivePath, 478baa3858d3f5d128a5c8466b700098109edcad5f2repo sync const CObjectVector<CArcItem> &arcItems, 479cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky Byte *processedItemsStatuses, 480baa3858d3f5d128a5c8466b700098109edcad5f2repo sync const CDirItems &dirItems, 481cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CDirItem *parentDirItem, 482baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CTempFiles &tempFiles, 483baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CUpdateErrorInfo &errorInfo, 484baa3858d3f5d128a5c8466b700098109edcad5f2repo sync IUpdateCallbackUI *callback) 485baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 486baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<IOutArchive> outArchive; 487cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int formatIndex = options.MethodMode.Type.FormatIndex; 488cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (arc) 489baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 490cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky formatIndex = arc->FormatIndex; 491cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (formatIndex < 0) 492cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 493cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CMyComPtr<IInArchive> archive2 = arc->Archive; 494baa3858d3f5d128a5c8466b700098109edcad5f2repo sync HRESULT result = archive2.QueryInterface(IID_IOutArchive, &outArchive); 495baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (result != S_OK) 496baa3858d3f5d128a5c8466b700098109edcad5f2repo sync throw kUpdateIsNotSupoorted; 497baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 498baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 499baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 500cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(codecs->CreateOutArchive(formatIndex, outArchive)); 501baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 502baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #ifdef EXTERNAL_CODECS 503baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 504baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<ISetCompressCodecsInfo> setCompressCodecsInfo; 505baa3858d3f5d128a5c8466b700098109edcad5f2repo sync outArchive.QueryInterface(IID_ISetCompressCodecsInfo, (void **)&setCompressCodecsInfo); 506baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (setCompressCodecsInfo) 507baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 508baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(setCompressCodecsInfo->SetCompressCodecsInfo(codecs)); 509baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 510baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 511baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #endif 512baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 513baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (outArchive == 0) 514baa3858d3f5d128a5c8466b700098109edcad5f2repo sync throw kUpdateIsNotSupoorted; 515baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 516baa3858d3f5d128a5c8466b700098109edcad5f2repo sync NFileTimeType::EEnum fileTimeType; 517baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt32 value; 518baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(outArchive->GetFileTimeType(&value)); 519baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 520cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky switch (value) 521baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 522baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kWindows: 523baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kUnix: 524baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kDOS: 525baa3858d3f5d128a5c8466b700098109edcad5f2repo sync fileTimeType = (NFileTimeType::EEnum)value; 526baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 527baa3858d3f5d128a5c8466b700098109edcad5f2repo sync default: 528baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 529baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 530baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 531cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 532cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CArcInfoEx &arcInfo = codecs->Formats[formatIndex]; 533cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.AltStreams.Val && !arcInfo.Flags_AltStreams()) 534cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 535cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.NtSecurity.Val && !arcInfo.Flags_NtSecure()) 536cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 537cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 538cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 539baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CRecordVector<CUpdatePair2> updatePairs2; 540baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 541cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UStringVector newNames; 542cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 543cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.RenamePairs.Size() != 0) 544cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 545cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, arcItems) 546cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 547cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CArcItem &ai = arcItems[i]; 548cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool needRename = false; 549cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString dest; 550cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (ai.Censored) 551cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 552cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (j, options.RenamePairs) 553cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 554cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CRenamePair &rp = options.RenamePairs[j]; 555cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (rp.GetNewPath(ai.IsDir, ai.Name, dest)) 556cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 557cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky needRename = true; 558cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky break; 559cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 560cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (ai.IsAltStream) 561cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 562cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int colonPos = ai.Name.ReverseFind(':'); 563cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int slashPosPos = GetReverseSlashPos(ai.Name); 564cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (colonPos > slashPosPos) 565cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 566cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString mainName = ai.Name.Left(colonPos); 567cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 568cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky actually we must improve that code to support cases 569cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky with folder renaming like: rn arc dir1\ dir2\ 570cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 571cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (rp.GetNewPath(false, mainName, dest)) 572cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 573cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky needRename = true; 574cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dest += ':'; 575cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dest += ai.Name.Ptr(colonPos + 1); 576cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky break; 577cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 578cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 579cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 580cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 581cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 582cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CUpdatePair2 up2; 583cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky up2.SetAs_NoChangeArcItem(ai.IndexInServer); 584cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (needRename) 585cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 586cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky up2.NewProps = true; 587cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(arc->IsItemAnti(i, up2.IsAnti)); 588cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky up2.NewNameIndex = newNames.Add(dest); 589cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 590cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updatePairs2.Add(up2); 591cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 592cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 593cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 594baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 595baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CRecordVector<CUpdatePair> updatePairs; 596baa3858d3f5d128a5c8466b700098109edcad5f2repo sync GetUpdatePairInfoList(dirItems, arcItems, fileTimeType, updatePairs); // must be done only once!!! 597baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // CUpdateProduceCallbackImp upCallback(&arcItems, callback); 598baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UpdateProduce(updatePairs, actionSet, updatePairs2, NULL /* &upCallback */); 599baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 600baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 601baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt32 numFiles = 0; 602cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, updatePairs2) 603baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (updatePairs2[i].NewData) 604baa3858d3f5d128a5c8466b700098109edcad5f2repo sync numFiles++; 605baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 606baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(callback->SetNumFiles(numFiles)); 607baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 608baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchiveUpdateCallback *updateCallbackSpec = new CArchiveUpdateCallback; 609baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<IArchiveUpdateCallback> updateCallback(updateCallbackSpec); 610baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 611cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->ShareForWrite = options.OpenShareForWrite; 612cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->StdInMode = options.StdInMode; 613baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->Callback = callback; 614cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 615cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (arc) 616cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 617cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // we set Archive to allow to transfer GetProperty requests back to DLL. 618cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->Archive = arc->Archive; 619cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->GetRawProps = arc->GetRawProps; 620cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->GetRootProps = arc->GetRootProps; 621cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 622cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 623baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->DirItems = &dirItems; 624cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->ParentDirItem = parentDirItem; 625cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 626cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->StoreNtSecurity = options.NtSecurity.Val; 627cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->StoreHardLinks = options.HardLinks.Val; 628cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->StoreSymLinks = options.SymLinks.Val; 629cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 630baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->ArcItems = &arcItems; 631baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->UpdatePairs = &updatePairs2; 632baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 633cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->ProcessedItemsStatuses = processedItemsStatuses; 634cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 635cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.RenamePairs.Size() != 0) 636cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky updateCallbackSpec->NewNames = &newNames; 637cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 638cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CMyComPtr<IOutStream> outSeekStream; 639baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<ISequentialOutStream> outStream; 640baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 641cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!options.StdOutMode) 642baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 643cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString dirPrefix; 644cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!GetOnlyDirPrefix(us2fs(archivePath.GetFinalPath()), dirPrefix)) 645baa3858d3f5d128a5c8466b700098109edcad5f2repo sync throw 1417161; 646cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CreateComplexDir(dirPrefix); 647baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 648baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 649baa3858d3f5d128a5c8466b700098109edcad5f2repo sync COutFileStream *outStreamSpec = NULL; 650baa3858d3f5d128a5c8466b700098109edcad5f2repo sync COutMultiVolStream *volStreamSpec = NULL; 651baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 652cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.VolumesSizes.Size() == 0) 653baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 654cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.StdOutMode) 655baa3858d3f5d128a5c8466b700098109edcad5f2repo sync outStream = new CStdOutFileStream; 656baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 657baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 658baa3858d3f5d128a5c8466b700098109edcad5f2repo sync outStreamSpec = new COutFileStream; 659cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky outSeekStream = outStreamSpec; 660cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky outStream = outSeekStream; 661baa3858d3f5d128a5c8466b700098109edcad5f2repo sync bool isOK = false; 662cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString realPath; 663baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (int i = 0; i < (1 << 16); i++) 664baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 665baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (archivePath.Temp) 666baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 667baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (i > 0) 668baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 669cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FChar s[16]; 670baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ConvertUInt32ToString(i, s); 671baa3858d3f5d128a5c8466b700098109edcad5f2repo sync archivePath.TempPostfix = s; 672baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 673baa3858d3f5d128a5c8466b700098109edcad5f2repo sync realPath = archivePath.GetTempPath(); 674baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 675baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 676cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky realPath = us2fs(archivePath.GetFinalPath()); 677baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (outStreamSpec->Create(realPath, false)) 678baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 679baa3858d3f5d128a5c8466b700098109edcad5f2repo sync tempFiles.Paths.Add(realPath); 680baa3858d3f5d128a5c8466b700098109edcad5f2repo sync isOK = true; 681baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 682baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 683baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (::GetLastError() != ERROR_FILE_EXISTS) 684baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 685baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!archivePath.Temp) 686baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 687baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 688baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!isOK) 689baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 690baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 691baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.FileName = realPath; 692baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot open file"; 693baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 694baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 695baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 696baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 697baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 698baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 699cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.StdOutMode) 700baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 701cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (arc && arc->GetGlobalOffset() > 0) 702cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 703cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 704baa3858d3f5d128a5c8466b700098109edcad5f2repo sync volStreamSpec = new COutMultiVolStream; 705cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky outSeekStream = volStreamSpec; 706cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky outStream = outSeekStream; 707cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky volStreamSpec->Sizes = options.VolumesSizes; 708cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky volStreamSpec->Prefix = us2fs(archivePath.GetFinalVolPath() + L"."); 709baa3858d3f5d128a5c8466b700098109edcad5f2repo sync volStreamSpec->TempFiles = &tempFiles; 710baa3858d3f5d128a5c8466b700098109edcad5f2repo sync volStreamSpec->Init(); 711baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 712baa3858d3f5d128a5c8466b700098109edcad5f2repo sync /* 713baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->VolumesSizes = volumesSizes; 714baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->VolName = archivePath.Prefix + archivePath.Name; 715baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!archivePath.VolExtension.IsEmpty()) 716baa3858d3f5d128a5c8466b700098109edcad5f2repo sync updateCallbackSpec->VolExt = UString(L'.') + archivePath.VolExtension; 717baa3858d3f5d128a5c8466b700098109edcad5f2repo sync */ 718baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 719baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 720cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(SetProperties(outArchive, options.MethodMode.Properties)); 721baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 722cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.SfxMode) 723baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 724baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CInFileStream *sfxStreamSpec = new CInFileStream; 725baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<IInStream> sfxStream(sfxStreamSpec); 726cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!sfxStreamSpec->Open(options.SfxModule)) 727baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 728baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 729baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot open SFX module"; 730cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.FileName = options.SfxModule; 731baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 732baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 733baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 734baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CMyComPtr<ISequentialOutStream> sfxOutStream; 735baa3858d3f5d128a5c8466b700098109edcad5f2repo sync COutFileStream *outStreamSpec = NULL; 736cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.VolumesSizes.Size() == 0) 737baa3858d3f5d128a5c8466b700098109edcad5f2repo sync sfxOutStream = outStream; 738baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 739baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 740baa3858d3f5d128a5c8466b700098109edcad5f2repo sync outStreamSpec = new COutFileStream; 741baa3858d3f5d128a5c8466b700098109edcad5f2repo sync sfxOutStream = outStreamSpec; 742cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString realPath = us2fs(archivePath.GetFinalPath()); 743baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!outStreamSpec->Create(realPath, false)) 744baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 745baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 746baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.FileName = realPath; 747baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot open file"; 748baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 749baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 750baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 751baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(NCompress::CopyStream(sfxStream, sfxOutStream, NULL)); 752baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (outStreamSpec) 753baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 754baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(outStreamSpec->Close()); 755baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 756baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 757baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 758cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CMyComPtr<ISequentialOutStream> tailStream; 759cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 760cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.SfxMode || !arc || arc->ArcStreamOffset == 0) 761cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStream = outStream; 762cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 763cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 764cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // Int64 globalOffset = arc->GetGlobalOffset(); 765cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(arc->InStream->Seek(0, STREAM_SEEK_SET, NULL)); 766cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(NCompress::CopyStream_ExactSize(arc->InStream, outStream, arc->ArcStreamOffset, NULL)); 767cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.StdOutMode) 768cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStream = outStream; 769cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 770cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 771cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CTailOutStream *tailStreamSpec = new CTailOutStream; 772cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStream = tailStreamSpec; 773cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStreamSpec->Stream = outSeekStream; 774cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStreamSpec->Offset = arc->ArcStreamOffset; 775cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tailStreamSpec->Init(); 776cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 777cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 778cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 779cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 780cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky HRESULT result = outArchive->UpdateItems(tailStream, updatePairs2.Size(), updateCallback); 781baa3858d3f5d128a5c8466b700098109edcad5f2repo sync callback->Finilize(); 782baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(result); 783cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 784cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 785cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.SetArcMTime) 786cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 787cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FILETIME ft; 788cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ft.dwLowDateTime = 0; 789cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ft.dwHighDateTime = 0; 790cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, updatePairs2) 791cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 792cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CUpdatePair2 &pair2 = updatePairs2[i]; 793cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const FILETIME *ft2 = NULL; 794cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (pair2.NewProps && pair2.DirIndex >= 0) 795cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ft2 = &dirItems.Items[pair2.DirIndex].MTime; 796cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else if (pair2.UseArcProps && pair2.ArcIndex >= 0) 797cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ft2 = &arcItems[pair2.ArcIndex].MTime; 798cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (ft2) 799cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 800cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (::CompareFileTime(&ft, ft2) < 0) 801cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ft = *ft2; 802cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 803cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 804cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (ft.dwLowDateTime != 0 || ft.dwHighDateTime != 0) 805cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 806cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (outStreamSpec) 807cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky outStreamSpec->SetMTime(&ft); 808cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else if (volStreamSpec) 809cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky volStreamSpec->SetMTime(&ft);; 810cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 811cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 812cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 813baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (outStreamSpec) 814baa3858d3f5d128a5c8466b700098109edcad5f2repo sync result = outStreamSpec->Close(); 815baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else if (volStreamSpec) 816baa3858d3f5d128a5c8466b700098109edcad5f2repo sync result = volStreamSpec->Close(); 817baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return result; 818baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 819baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 820cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic HRESULT EnumerateInArchiveItems( 821cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // bool storeStreamsMode, 822cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const NWildcard::CCensor &censor, 823baa3858d3f5d128a5c8466b700098109edcad5f2repo sync const CArc &arc, 824baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CObjectVector<CArcItem> &arcItems) 825baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 826baa3858d3f5d128a5c8466b700098109edcad5f2repo sync arcItems.Clear(); 827baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UInt32 numItems; 828baa3858d3f5d128a5c8466b700098109edcad5f2repo sync IInArchive *archive = arc.Archive; 829baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(archive->GetNumberOfItems(&numItems)); 830cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky arcItems.ClearAndReserve(numItems); 831baa3858d3f5d128a5c8466b700098109edcad5f2repo sync for (UInt32 i = 0; i < numItems; i++) 832baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 833baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArcItem ai; 834baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 835baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(arc.GetItemPath(i, ai.Name)); 836cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(Archive_IsItem_Folder(archive, i, ai.IsDir)); 837cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(Archive_IsItem_AltStream(archive, i, ai.IsAltStream)); 838cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 839cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!storeStreamsMode && ai.IsAltStream) 840cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky continue; 841cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 842cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ai.Censored = censor.CheckPath(ai.IsAltStream, ai.Name, !ai.IsDir); 843baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(arc.GetItemMTime(i, ai.MTime, ai.MTimeDefined)); 844cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(arc.GetItemSize(i, ai.Size, ai.SizeDefined)); 845baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 846baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 847baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CPropVariant prop; 848baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(archive->GetProperty(i, kpidTimeType, &prop)); 849baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (prop.vt == VT_UI4) 850baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 851baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ai.TimeType = (int)(NFileTimeType::EEnum)prop.ulVal; 852cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky switch (ai.TimeType) 853baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 854baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kWindows: 855baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kUnix: 856baa3858d3f5d128a5c8466b700098109edcad5f2repo sync case NFileTimeType::kDOS: 857baa3858d3f5d128a5c8466b700098109edcad5f2repo sync break; 858baa3858d3f5d128a5c8466b700098109edcad5f2repo sync default: 859baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 860baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 861baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 862baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 863baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 864baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ai.IndexInServer = i; 865cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky arcItems.AddInReserved(ai); 866baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 867baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return S_OK; 868baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 869baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 870cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystruct CEnumDirItemUpdateCallback: public IEnumDirItemCallback 871baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 872cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky IUpdateCallbackUI2 *Callback; 873cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky HRESULT ScanProgress(UInt64 numFolders, UInt64 numFiles, UInt64 totalSize, const wchar_t *path, bool isDir) 874baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 875cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return Callback->ScanProgress(numFolders, numFiles, totalSize, path, isDir); 876baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 877cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky}; 878baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 879baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#if defined(_WIN32) && !defined(UNDER_CE) 880cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 881cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#include <mapi.h> 882cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 883cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#endif 884cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 885cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystruct CRefSortPair 886baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 887cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int Len; 888cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int Index; 889baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}; 890baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 891cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky#define RINOZ(x) { int __tt = (x); if (__tt != 0) return __tt; } 892cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 893cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic int CompareRefSortPair(const CRefSortPair *a1, const CRefSortPair *a2, void *) 894baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 895cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOZ(-MyCompare(a1->Len, a2->Len)); 896cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return MyCompare(a1->Index, a2->Index); 897cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 898cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 899cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckystatic int GetNumSlashes(const FChar *s) 900cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky{ 901cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (int numSlashes = 0;;) 902baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 903cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FChar c = *s++; 904cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (c == 0) 905cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return numSlashes; 906cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if ( 907cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #ifdef _WIN32 908cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky c == FTEXT('\\') || 909cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 910cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky c == FTEXT('/')) 911cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky numSlashes++; 912baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 913cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky} 914baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 915baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef _WIN32 916cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbeckyvoid ConvertToLongNames(NWildcard::CCensor &censor); 917baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif 918baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 919baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT UpdateArchive( 920baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CCodecs *codecs, 921cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CObjectVector<COpenType> &types, 922cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const UString &cmdArcPath2, 923cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NWildcard::CCensor &censor, 924baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CUpdateOptions &options, 925baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CUpdateErrorInfo &errorInfo, 926baa3858d3f5d128a5c8466b700098109edcad5f2repo sync IOpenCallbackUI *openCallback, 927cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky IUpdateCallbackUI2 *callback, 928cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool needSetPath) 929baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{ 930baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.StdOutMode && options.EMailMode) 931baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 932baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 933cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (types.Size() > 1) 934cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 935cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 936cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool renameMode = !options.RenamePairs.IsEmpty(); 937cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (renameMode) 938cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 939cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.Commands.Size() != 1) 940cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 941cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 942cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 943cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.DeleteAfterCompressing) 944cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 945cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.Commands.Size() != 1) 946cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 947cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CActionSet &as = options.Commands[0].ActionSet; 948cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (int i = 2; i < NPairState::kNumValues; i++) 949cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (as.StateActions[i] != NPairAction::kCompress) 950cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 951cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 952cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 953cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky censor.AddPathsToCensor(options.PathMode); 954cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #ifdef _WIN32 955cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ConvertToLongNames(censor); 956cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 957cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky censor.ExtendExclude(); 958cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 959cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 960cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.VolumesSizes.Size() > 0 && (options.EMailMode /* || options.SfxMode */)) 961baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_NOTIMPL; 962baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 963baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.SfxMode) 964baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 965baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CProperty property; 966baa3858d3f5d128a5c8466b700098109edcad5f2repo sync property.Name = L"rsfx"; 967baa3858d3f5d128a5c8466b700098109edcad5f2repo sync property.Value = L"on"; 968baa3858d3f5d128a5c8466b700098109edcad5f2repo sync options.MethodMode.Properties.Add(property); 969baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.SfxModule.IsEmpty()) 970baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 971baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"SFX file is not specified"; 972baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 973baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 974cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool found = false; 975cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.SfxModule.Find(FCHAR_PATH_SEPARATOR) < 0) 976baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 977cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const FString fullName = NDLL::GetModuleDirPrefix() + options.SfxModule; 978cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (NFind::DoesFileExist(fullName)) 979cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 980cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.SfxModule = fullName; 981cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky found = true; 982cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 983cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 984cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!found) 985cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 986cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!NFind::DoesFileExist(options.SfxModule)) 987cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 988cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.SystemError = ::GetLastError(); 989cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.Message = L"7-Zip cannot find specified SFX module"; 990cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.FileName = options.SfxModule; 991cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 992cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 993baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 994baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 995baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 996baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchiveLink arcLink; 997baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 998cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 999cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (needSetPath) 1000cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1001cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!options.InitFormatIndex(codecs, types, cmdArcPath2) || 1002cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky !options.SetArcPath(codecs, cmdArcPath2)) 1003cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1004cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1005cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString arcPath = options.ArchivePath.GetFinalPath(); 1006cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1007cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (cmdArcPath2.IsEmpty()) 1008cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1009cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type.FormatIndex < 0) 1010cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky throw "type of archive is not specified"; 1011cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1012cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1013baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1014cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NFind::CFileInfo fi; 1015cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!fi.Find(us2fs(arcPath))) 1016cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1017cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (renameMode) 1018cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky throw "can't find archive";; 1019cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type.FormatIndex < 0) 1020cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1021cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!options.SetArcPath(codecs, cmdArcPath2)) 1022cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1023cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1024cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1025cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1026baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1027baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (fi.IsDir()) 1028baa3858d3f5d128a5c8466b700098109edcad5f2repo sync throw "there is no such archive"; 1029cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (fi.IsDevice) 1030cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1031baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.VolumesSizes.Size() > 0) 1032baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_NOTIMPL; 1033cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CObjectVector<COpenType> types; 1034cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // change it. 1035cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type_Defined) 1036cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky types.Add(options.MethodMode.Type); 1037cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // We need to set Properties to open archive only in some cases (WIM archives). 1038cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1039cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CIntVector excl; 1040cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky COpenOptions op; 1041cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #ifndef _SFX 1042cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.props = &options.MethodMode.Properties; 1043cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 1044cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.codecs = codecs; 1045cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.types = &types; 1046cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.excludedFormats = ! 1047cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.stdInMode = false; 1048cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.stream = NULL; 1049cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky op.filePath = arcPath; 1050cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1051cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky HRESULT result = arcLink.Open2(op, openCallback); 1052cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1053baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (result == E_ABORT) 1054baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return result; 1055cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1056cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const wchar_t *errorArcType = NULL; 1057cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (arcLink.NonOpen_ErrorInfo.ErrorFormatIndex > 0) 1058cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorArcType = codecs->Formats[arcLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name; 1059cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(callback->OpenResult(arcPath, result, errorArcType)); 1060cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1061cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (result == S_FALSE) 1062cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 1063cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1064baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(result); 1065baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (arcLink.VolumePaths.Size() > 1) 1066baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1067baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = (DWORD)E_NOTIMPL; 1068baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"Updating for multivolume archives is not implemented"; 1069baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_NOTIMPL; 1070baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1071baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1072baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArc &arc = arcLink.Arcs.Back(); 1073baa3858d3f5d128a5c8466b700098109edcad5f2repo sync arc.MTimeDefined = !fi.IsDevice; 1074baa3858d3f5d128a5c8466b700098109edcad5f2repo sync arc.MTime = fi.MTime; 1075cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1076cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (arc.ErrorInfo.ThereIsTail) 1077cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1078cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.SystemError = (DWORD)E_NOTIMPL; 1079cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.Message = L"There is some data block after the end of the archive"; 1080cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1081cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1082cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type.FormatIndex < 0) 1083cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1084cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.MethodMode.Type.FormatIndex = arcLink.GetArc()->FormatIndex; 1085cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!options.SetArcPath(codecs, cmdArcPath2)) 1086cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1087cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1088baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1089baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1090cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1091cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type.FormatIndex < 0) 1092baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1093cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.MethodMode.Type.FormatIndex = codecs->FindFormatForArchiveType(kDefaultArcType); 1094cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.MethodMode.Type.FormatIndex < 0) 1095cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_NOTIMPL; 1096baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1097baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1098cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool thereIsInArchive = arcLink.IsOpen; 1099cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!thereIsInArchive && renameMode) 1100cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 1101cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1102baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CDirItems dirItems; 1103cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CDirItem parentDirItem; 1104cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CDirItem *parentDirItem_Ptr = NULL; 1105cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1106cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1107cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector requestedPaths; 1108cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector *requestedPaths_Ptr = NULL; 1109cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.DeleteAfterCompressing) 1110cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky requestedPaths_Ptr = &requestedPaths; 1111cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1112cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1113baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.StdInMode) 1114baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1115baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CDirItem di; 1116baa3858d3f5d128a5c8466b700098109edcad5f2repo sync di.Name = options.StdInFileName; 1117baa3858d3f5d128a5c8466b700098109edcad5f2repo sync di.Size = (UInt64)(Int64)-1; 1118baa3858d3f5d128a5c8466b700098109edcad5f2repo sync di.Attrib = 0; 1119baa3858d3f5d128a5c8466b700098109edcad5f2repo sync NTime::GetCurUtcFileTime(di.MTime); 1120baa3858d3f5d128a5c8466b700098109edcad5f2repo sync di.CTime = di.ATime = di.MTime; 1121baa3858d3f5d128a5c8466b700098109edcad5f2repo sync dirItems.Items.Add(di); 1122baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1123baa3858d3f5d128a5c8466b700098109edcad5f2repo sync else 1124baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1125baa3858d3f5d128a5c8466b700098109edcad5f2repo sync bool needScanning = false; 1126cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!renameMode) 1127cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, options.Commands) 1128baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.Commands[i].ActionSet.NeedScanning()) 1129baa3858d3f5d128a5c8466b700098109edcad5f2repo sync needScanning = true; 1130baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (needScanning) 1131baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1132baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CEnumDirItemUpdateCallback enumCallback; 1133baa3858d3f5d128a5c8466b700098109edcad5f2repo sync enumCallback.Callback = callback; 1134baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(callback->StartScanning()); 1135cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1136cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems.SymLinks = options.SymLinks.Val; 1137cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1138cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #if defined(_WIN32) && !defined(UNDER_CE) 1139cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems.ReadSecure = options.NtSecurity.Val; 1140cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 1141cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1142cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems.ScanAltStreams = options.AltStreams.Val; 1143cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky HRESULT res = EnumerateItems(censor, 1144cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.PathMode, 1145cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.AddPathPrefix, 1146cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems, &enumCallback); 1147cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FOR_VECTOR (i, dirItems.ErrorPaths) 1148baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1149cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(callback->CanNotFindError(fs2us(dirItems.ErrorPaths[i]), dirItems.ErrorCodes[i])); 1150baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1151baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (res != S_OK) 1152baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1153baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (res != E_ABORT) 1154baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"Scanning error"; 1155baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return res; 1156baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1157baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(callback->FinishScanning()); 1158cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1159cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (censor.Pairs.Size() == 1) 1160cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1161cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NFind::CFileInfo fi; 1162cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString prefix = us2fs(censor.Pairs[0].Prefix) + FTEXT("."); 1163cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // UString prefix = censor.Pairs[0].Prefix; 1164cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1165cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (prefix.Back() == WCHAR_PATH_SEPARATOR) 1166cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1167cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky prefix.DeleteBack(); 1168cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1169cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1170cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (fi.Find(prefix)) 1171cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (fi.IsDir()) 1172cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1173cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.Size = fi.Size; 1174cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.CTime = fi.CTime; 1175cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.ATime = fi.ATime; 1176cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.MTime = fi.MTime; 1177cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.Attrib = fi.Attrib; 1178cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem_Ptr = &parentDirItem; 1179cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1180cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky int secureIndex = -1; 1181cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #if defined(_WIN32) && !defined(UNDER_CE) 1182cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.NtSecurity.Val) 1183cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems.AddSecurityItem(prefix, secureIndex); 1184cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky #endif 1185cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem.SecureIndex = secureIndex; 1186cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1187cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem_Ptr = &parentDirItem; 1188cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1189cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1190baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1191baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1192baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1193cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString tempDirPrefix; 1194baa3858d3f5d128a5c8466b700098109edcad5f2repo sync bool usesTempDir = false; 1195baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1196baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #ifdef _WIN32 1197cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CTempDir tempDirectory; 1198baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.EMailMode && options.EMailRemoveAfter) 1199baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1200baa3858d3f5d128a5c8466b700098109edcad5f2repo sync tempDirectory.Create(kTempFolderPrefix); 1201baa3858d3f5d128a5c8466b700098109edcad5f2repo sync tempDirPrefix = tempDirectory.GetPath(); 1202baa3858d3f5d128a5c8466b700098109edcad5f2repo sync NormalizeDirPathPrefix(tempDirPrefix); 1203baa3858d3f5d128a5c8466b700098109edcad5f2repo sync usesTempDir = true; 1204baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1205baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #endif 1206baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1207baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CTempFiles tempFiles; 1208baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1209baa3858d3f5d128a5c8466b700098109edcad5f2repo sync bool createTempFile = false; 1210baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1211baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!options.StdOutMode && options.UpdateArchiveItself) 1212baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1213baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchivePath &ap = options.Commands[0].ArchivePath; 1214baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ap = options.ArchivePath; 1215baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // if ((archive != 0 && !usesTempDir) || !options.WorkingDir.IsEmpty()) 1216baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if ((thereIsInArchive || !options.WorkingDir.IsEmpty()) && !usesTempDir && options.VolumesSizes.Size() == 0) 1217baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1218baa3858d3f5d128a5c8466b700098109edcad5f2repo sync createTempFile = true; 1219baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ap.Temp = true; 1220baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!options.WorkingDir.IsEmpty()) 1221baa3858d3f5d128a5c8466b700098109edcad5f2repo sync ap.TempPrefix = options.WorkingDir; 1222cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1223cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ap.TempPrefix = us2fs(ap.Prefix); 1224cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky NormalizeDirPathPrefix(ap.TempPrefix); 1225baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1226baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1227baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1228cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned i; 1229cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < options.Commands.Size(); i++) 1230baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1231baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchivePath &ap = options.Commands[i].ArchivePath; 1232baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (usesTempDir) 1233baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1234baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // Check it 1235cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky ap.Prefix = fs2us(tempDirPrefix); 1236baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // ap.Temp = true; 1237baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // ap.TempPrefix = tempDirPrefix; 1238baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1239baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (!options.StdOutMode && 1240baa3858d3f5d128a5c8466b700098109edcad5f2repo sync (i > 0 || !createTempFile)) 1241baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1242cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const FString path = us2fs(ap.GetFinalPath()); 1243baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (NFind::DoesFileOrDirExist(path)) 1244baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1245baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = 0; 1246baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"The file already exists"; 1247baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.FileName = path; 1248baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1249baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1250baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1251baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1252baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1253baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CObjectVector<CArcItem> arcItems; 1254baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (thereIsInArchive) 1255baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1256cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(EnumerateInArchiveItems( 1257cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // options.StoreAltStreams, 1258cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky censor, arcLink.Arcs.Back(), arcItems)); 1259cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1260cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1261cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1262cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector processedFilePaths; 1263cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector *processedFilePaths_Ptr = NULL; 1264cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.DeleteAfterCompressing) 1265cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky processedFilePaths_Ptr = &processedFilePaths; 1266cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1267cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1268cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CByteBuffer processedItems; 1269cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.DeleteAfterCompressing) 1270cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1271cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned num = dirItems.Items.Size(); 1272cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky processedItems.Alloc(num); 1273cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < num; i++) 1274cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky processedItems[i] = 0; 1275cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1276cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1277cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < options.Commands.Size(); i++) 1278cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1279cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CArc *arc = thereIsInArchive ? arcLink.GetArc() : 0; 1280cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // IInArchiveExtra *archiveExtra = thereIsInArchive ? arcLink.GetArchiveExtra() : 0; 1281cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // IArchiveGetRootProps *archiveGetRootProps = thereIsInArchive ? arcLink.GetArchiveGetRootProps() : 0; 1282cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CUpdateArchiveCommand &command = options.Commands[i]; 1283cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString name; 1284cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky bool isUpdating; 1285cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.StdOutMode) 1286cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1287cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky name = L"stdout"; 1288cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky isUpdating = arc != 0; 1289cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1290cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1291cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1292cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky name = command.ArchivePath.GetFinalPath(); 1293cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky isUpdating = (i == 0 && options.UpdateArchiveItself && arc != 0); 1294cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1295cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(callback->StartArchive(name, isUpdating)) 1296cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1297cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(Compress(options, 1298cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky codecs, 1299cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky command.ActionSet, 1300cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky arc, 1301cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky command.ArchivePath, 1302cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky arcItems, 1303cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky options.DeleteAfterCompressing ? (Byte *)processedItems : NULL, 1304cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1305cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky dirItems, 1306cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky parentDirItem_Ptr, 1307cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1308cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky tempFiles, 1309cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo, callback)); 1310cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1311cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RINOK(callback->FinishArchive()); 1312baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1313baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1314baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1315baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (thereIsInArchive) 1316baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1317baa3858d3f5d128a5c8466b700098109edcad5f2repo sync RINOK(arcLink.Close()); 1318baa3858d3f5d128a5c8466b700098109edcad5f2repo sync arcLink.Release(); 1319baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1320baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1321baa3858d3f5d128a5c8466b700098109edcad5f2repo sync tempFiles.Paths.Clear(); 1322baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (createTempFile) 1323baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1324baa3858d3f5d128a5c8466b700098109edcad5f2repo sync try 1325baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1326baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchivePath &ap = options.Commands[0].ArchivePath; 1327cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const FString &tempPath = ap.GetTempPath(); 1328baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (thereIsInArchive) 1329cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!DeleteFileAlways(us2fs(arcPath))) 1330baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1331baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 1332baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot delete the file"; 1333cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.FileName = us2fs(arcPath); 1334baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1335baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1336cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!MyMoveFile(tempPath, us2fs(arcPath))) 1337baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1338baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 1339baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot move the file"; 1340baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.FileName = tempPath; 1341cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.FileName2 = us2fs(arcPath); 1342baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1343baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1344baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1345baa3858d3f5d128a5c8466b700098109edcad5f2repo sync catch(...) 1346baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1347baa3858d3f5d128a5c8466b700098109edcad5f2repo sync throw; 1348baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1349baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1350baa3858d3f5d128a5c8466b700098109edcad5f2repo sync 1351cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1352baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #if defined(_WIN32) && !defined(UNDER_CE) 1353baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (options.EMailMode) 1354baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1355baa3858d3f5d128a5c8466b700098109edcad5f2repo sync NDLL::CLibrary mapiLib; 1356cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!mapiLib.Load(FTEXT("Mapi32.dll"))) 1357baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1358baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 1359baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot load Mapi32.dll"; 1360baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1361baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1362cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1363cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1364cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky LPMAPISENDDOCUMENTS fnSend = (LPMAPISENDDOCUMENTS)mapiLib.GetProc("MAPISendDocuments"); 1365baa3858d3f5d128a5c8466b700098109edcad5f2repo sync if (fnSend == 0) 1366baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1367baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 1368baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"7-Zip cannot find MAPISendDocuments function"; 1369baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1370baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1371cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1372cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky LPMAPISENDMAIL sendMail = (LPMAPISENDMAIL)mapiLib.GetProc("MAPISendMail"); 1373cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (sendMail == 0) 1374cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1375cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.SystemError = ::GetLastError(); 1376cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.Message = L"7-Zip cannot find MAPISendMail function"; 1377cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 1378cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1379cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1380cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector fullPaths; 1381cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky unsigned i; 1382cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < options.Commands.Size(); i++) 1383baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1384baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CArchivePath &ap = options.Commands[i].ArchivePath; 1385cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString arcPath; 1386cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!MyGetFullPathName(us2fs(ap.GetFinalPath()), arcPath)) 1387baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1388baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.SystemError = ::GetLastError(); 1389baa3858d3f5d128a5c8466b700098109edcad5f2repo sync errorInfo.Message = L"GetFullPathName error"; 1390baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return E_FAIL; 1391baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1392baa3858d3f5d128a5c8466b700098109edcad5f2repo sync fullPaths.Add(arcPath); 1393baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1394baa3858d3f5d128a5c8466b700098109edcad5f2repo sync CCurrentDirRestorer curDirRestorer; 1395cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < fullPaths.Size(); i++) 1396baa3858d3f5d128a5c8466b700098109edcad5f2repo sync { 1397cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky UString arcPath = fs2us(fullPaths[i]); 1398baa3858d3f5d128a5c8466b700098109edcad5f2repo sync UString fileName = ExtractFileNameFromPath(arcPath); 1399baa3858d3f5d128a5c8466b700098109edcad5f2repo sync AString path = GetAnsiString(arcPath); 1400baa3858d3f5d128a5c8466b700098109edcad5f2repo sync AString name = GetAnsiString(fileName); 1401baa3858d3f5d128a5c8466b700098109edcad5f2repo sync // Warning!!! MAPISendDocuments function changes Current directory 1402cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // fnSend(0, ";", (LPSTR)(LPCSTR)path, (LPSTR)(LPCSTR)name, 0); 1403cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1404cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MapiFileDesc f; 1405cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky memset(&f, 0, sizeof(f)); 1406cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky f.nPosition = 0xFFFFFFFF; 1407cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky f.lpszPathName = (char *)(const char *)path; 1408cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky f.lpszFileName = (char *)(const char *)name; 1409cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1410cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MapiMessage m; 1411cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky memset(&m, 0, sizeof(m)); 1412cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky m.nFileCount = 1; 1413cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky m.lpFiles = &f; 1414cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1415cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const AString addr = GetAnsiString(options.EMailAddress); 1416cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky MapiRecipDesc rec; 1417cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (!addr.IsEmpty()) 1418cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1419cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky memset(&rec, 0, sizeof(rec)); 1420cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky rec.ulRecipClass = MAPI_TO; 1421cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky rec.lpszAddress = (char *)(const char *)addr; 1422cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky m.nRecipCount = 1; 1423cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky m.lpRecips = &rec; 1424cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1425cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1426cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky sendMail((LHANDLE)0, 0, &m, MAPI_DIALOG, 0); 1427baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1428baa3858d3f5d128a5c8466b700098109edcad5f2repo sync } 1429baa3858d3f5d128a5c8466b700098109edcad5f2repo sync #endif 1430cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1431cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (options.DeleteAfterCompressing) 1432cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1433cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CRecordVector<CRefSortPair> pairs; 1434cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FStringVector foldersNames; 1435cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < dirItems.Items.Size(); i++) 1436cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1437cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky const CDirItem &dirItem = dirItems.Items[i]; 1438cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString phyPath = us2fs(dirItems.GetPhyPath(i)); 1439cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (dirItem.IsDir()) 1440cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1441cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky CRefSortPair pair; 1442cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky pair.Index = i; 1443cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky pair.Len = GetNumSlashes(phyPath); 1444cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky pairs.Add(pair); 1445cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1446cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1447cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1448cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (processedItems[i] != 0 || dirItem.Size == 0) 1449cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1450cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky DeleteFileAlways(phyPath); 1451cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1452cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky else 1453cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1454cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // file was skipped 1455cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky /* 1456cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.SystemError = 0; 1457cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.Message = L"file was not processed"; 1458cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky errorInfo.FileName = phyPath; 1459cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky return E_FAIL; 1460cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky */ 1461cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1462cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1463cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1464cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky 1465cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky pairs.Sort(CompareRefSortPair, NULL); 1466cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky for (i = 0; i < pairs.Size(); i++) 1467cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1468cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky FString phyPath = us2fs(dirItems.GetPhyPath(pairs[i].Index)); 1469cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky if (NFind::DoesDirExist(phyPath)) 1470cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky { 1471cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky // printf("delete %S\n", phyPath); 1472cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky RemoveDir(phyPath); 1473cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1474cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1475cd66d540cead3f8200b0c73bad9c276d67896c3dDavid Srbecky } 1476baa3858d3f5d128a5c8466b700098109edcad5f2repo sync return S_OK; 1477baa3858d3f5d128a5c8466b700098109edcad5f2repo sync} 1478