Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/kornelski/7z.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/CPP
diff options
context:
space:
mode:
authorIgor Pavlov <ipavlov@users.sourceforge.net>2009-06-02 04:00:00 +0400
committerKornel LesiƄski <kornel@geekhood.net>2016-05-28 02:15:59 +0300
commit829409452d85cd6dd9dfc9151f109d6e13a2bb1c (patch)
treee0acaea47044d167f35fa197584dee1bde41c329 /CPP
parent8874e4fbc9faabdcff719b9b2ac8ebad4f282bbe (diff)
9.04 beta
Diffstat (limited to 'CPP')
-rwxr-xr-xCPP/7zip/Archive/7z/7z.dsp4
-rwxr-xr-xCPP/7zip/Archive/7z/7zEncode.cpp26
-rwxr-xr-xCPP/7zip/Archive/7z/7zFolderOutStream.cpp154
-rwxr-xr-xCPP/7zip/Archive/7z/7zFolderOutStream.h48
-rwxr-xr-xCPP/7zip/Archive/7z/7zHandler.cpp148
-rwxr-xr-xCPP/7zip/Archive/7z/7zHandler.h8
-rwxr-xr-xCPP/7zip/Archive/7z/7zHandlerOut.cpp70
-rwxr-xr-xCPP/7zip/Archive/7z/7zIn.cpp27
-rwxr-xr-xCPP/7zip/Archive/7z/7zIn.h8
-rwxr-xr-xCPP/7zip/Archive/7z/7zOut.cpp10
-rwxr-xr-xCPP/7zip/Archive/7z/7zOut.h8
-rwxr-xr-xCPP/7zip/Archive/7z/7zUpdate.cpp773
-rwxr-xr-xCPP/7zip/Archive/7z/7zUpdate.h10
-rwxr-xr-xCPP/7zip/Archive/7z/makefile2
-rwxr-xr-xCPP/7zip/Archive/ArchiveExports.cpp9
-rwxr-xr-xCPP/7zip/Archive/ArjHandler.cpp25
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2Handler.cpp216
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2Handler.h68
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2HandlerOut.cpp156
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2Item.h20
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2Update.cpp74
-rwxr-xr-xCPP/7zip/Archive/BZip2/BZip2Update.h26
-rwxr-xr-xCPP/7zip/Archive/BZip2/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/BZip2/bz2Register.cpp18
-rwxr-xr-xCPP/7zip/Archive/Bz2Handler.cpp428
-rwxr-xr-xCPP/7zip/Archive/Cab/CabBlockInStream.cpp3
-rwxr-xr-xCPP/7zip/Archive/Cab/CabIn.cpp6
-rwxr-xr-xCPP/7zip/Archive/Cab/CabIn.h2
-rwxr-xr-xCPP/7zip/Archive/Chm/ChmIn.cpp29
-rwxr-xr-xCPP/7zip/Archive/Chm/ChmIn.h6
-rwxr-xr-xCPP/7zip/Archive/Com/ComHandler.cpp198
-rwxr-xr-xCPP/7zip/Archive/Com/ComHandler.h10
-rwxr-xr-xCPP/7zip/Archive/Com/ComIn.cpp130
-rwxr-xr-xCPP/7zip/Archive/Com/ComIn.h37
-rwxr-xr-xCPP/7zip/Archive/Common/HandlerOut.cpp119
-rwxr-xr-xCPP/7zip/Archive/Common/HandlerOut.h2
-rwxr-xr-xCPP/7zip/Archive/Common/InStreamWithCRC.h12
-rwxr-xr-xCPP/7zip/Archive/Common/OutStreamWithCRC.cpp20
-rwxr-xr-xCPP/7zip/Archive/Common/OutStreamWithCRC.h8
-rwxr-xr-xCPP/7zip/Archive/Common/OutStreamWithSha1.cpp20
-rwxr-xr-xCPP/7zip/Archive/Common/OutStreamWithSha1.h8
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioHandler.cpp240
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioHandler.h30
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioHeader.cpp23
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioHeader.h70
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioIn.cpp272
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioIn.h41
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioItem.h55
-rwxr-xr-xCPP/7zip/Archive/Cpio/CpioRegister.cpp13
-rwxr-xr-xCPP/7zip/Archive/Cpio/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/CpioHandler.cpp625
-rwxr-xr-xCPP/7zip/Archive/DebHandler.cpp91
-rwxr-xr-xCPP/7zip/Archive/DllExports2.cpp3
-rwxr-xr-xCPP/7zip/Archive/ElfHandler.cpp30
-rwxr-xr-xCPP/7zip/Archive/FatHandler.cpp983
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipHandler.cpp284
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipHandler.h63
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipHandlerOut.cpp202
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipHeader.cpp20
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipHeader.h85
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipIn.cpp119
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipIn.h30
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipItem.h59
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipOut.cpp65
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipOut.h29
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipRegister.cpp18
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipUpdate.cpp112
-rwxr-xr-xCPP/7zip/Archive/GZip/GZipUpdate.h37
-rwxr-xr-xCPP/7zip/Archive/GZip/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/GzHandler.cpp820
-rwxr-xr-xCPP/7zip/Archive/IArchive.h12
-rwxr-xr-xCPP/7zip/Archive/Icons/fat.icobin0 -> 3638 bytes
-rwxr-xr-xCPP/7zip/Archive/Icons/ntfs.icobin0 -> 3638 bytes
-rwxr-xr-xCPP/7zip/Archive/Icons/vhd.icobin0 -> 3638 bytes
-rwxr-xr-xCPP/7zip/Archive/Icons/xar.icobin3638 -> 3638 bytes
-rwxr-xr-xCPP/7zip/Archive/Icons/xz.icobin0 -> 3638 bytes
-rwxr-xr-xCPP/7zip/Archive/Iso/IsoHandler.cpp57
-rwxr-xr-xCPP/7zip/Archive/Iso/IsoHandler.h17
-rwxr-xr-xCPP/7zip/Archive/Iso/IsoIn.cpp21
-rwxr-xr-xCPP/7zip/Archive/Iso/IsoIn.h12
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhCRC.cpp43
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhCRC.h27
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhHandler.cpp387
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhHandler.h30
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhHeader.h19
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhIn.cpp172
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhIn.h29
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhItem.h172
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.cpp27
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.h38
-rwxr-xr-xCPP/7zip/Archive/Lzh/LzhRegister.cpp13
-rwxr-xr-xCPP/7zip/Archive/Lzh/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/LzhHandler.cpp783
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaArcRegister.cpp14
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp86
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaFiltersDecode.h26
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaHandler.cpp243
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaHandler.h69
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaIn.cpp56
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaIn.h16
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaItem.h27
-rwxr-xr-xCPP/7zip/Archive/Lzma/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/LzmaHandler.cpp436
-rwxr-xr-xCPP/7zip/Archive/MachoHandler.cpp38
-rwxr-xr-xCPP/7zip/Archive/MbrHandler.cpp508
-rwxr-xr-xCPP/7zip/Archive/MubHandler.cpp35
-rwxr-xr-xCPP/7zip/Archive/NtfsHandler.cpp1725
-rwxr-xr-xCPP/7zip/Archive/PeHandler.cpp27
-rwxr-xr-xCPP/7zip/Archive/Rar/RarHandler.cpp5
-rwxr-xr-xCPP/7zip/Archive/Rar/RarIn.cpp8
-rwxr-xr-xCPP/7zip/Archive/Rar/RarVolumeInStream.cpp10
-rwxr-xr-xCPP/7zip/Archive/RpmHandler.cpp128
-rwxr-xr-xCPP/7zip/Archive/Split/SplitHandler.h37
-rwxr-xr-xCPP/7zip/Archive/Split/SplitHandlerOut.cpp102
-rwxr-xr-xCPP/7zip/Archive/Split/SplitRegister.cpp20
-rwxr-xr-xCPP/7zip/Archive/Split/StdAfx.h8
-rwxr-xr-xCPP/7zip/Archive/SplitHandler.cpp (renamed from CPP/7zip/Archive/Split/SplitHandler.cpp)139
-rwxr-xr-xCPP/7zip/Archive/Tar/TarHandler.cpp193
-rwxr-xr-xCPP/7zip/Archive/Tar/TarHandler.h36
-rwxr-xr-xCPP/7zip/Archive/Tar/TarHandlerOut.cpp100
-rwxr-xr-xCPP/7zip/Archive/Tar/TarIn.cpp23
-rwxr-xr-xCPP/7zip/Archive/Tar/TarItem.h10
-rwxr-xr-xCPP/7zip/Archive/Tar/TarOut.cpp15
-rwxr-xr-xCPP/7zip/Archive/Tar/TarUpdate.cpp23
-rwxr-xr-xCPP/7zip/Archive/Tar/TarUpdate.h10
-rwxr-xr-xCPP/7zip/Archive/Udf/UdfHandler.cpp276
-rwxr-xr-xCPP/7zip/Archive/Udf/UdfHandler.h4
-rwxr-xr-xCPP/7zip/Archive/Udf/UdfIn.cpp22
-rwxr-xr-xCPP/7zip/Archive/VhdHandler.cpp731
-rwxr-xr-xCPP/7zip/Archive/Wim/WimIn.cpp11
-rwxr-xr-xCPP/7zip/Archive/XzHandler.cpp714
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipAddCommon.cpp3
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipHandler.cpp160
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipHeader.h15
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipIn.cpp175
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipIn.h12
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipItem.cpp25
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipItem.h12
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipRegister.cpp2
-rwxr-xr-xCPP/7zip/Archive/Zip/ZipUpdate.cpp3
-rwxr-xr-xCPP/7zip/Bundles/Alone/Alone.dsp454
-rwxr-xr-xCPP/7zip/Bundles/Alone/makefile64
-rwxr-xr-xCPP/7zip/Bundles/Alone7z/makefile52
-rwxr-xr-xCPP/7zip/Bundles/Format7z/makefile14
-rwxr-xr-xCPP/7zip/Bundles/Format7zExtract/makefile11
-rwxr-xr-xCPP/7zip/Bundles/Format7zExtractR/makefile7
-rwxr-xr-xCPP/7zip/Bundles/Format7zF/Format7z.dsp481
-rwxr-xr-xCPP/7zip/Bundles/Format7zF/makefile89
-rwxr-xr-xCPP/7zip/Bundles/Format7zF/resource.rc6
-rwxr-xr-xCPP/7zip/Bundles/Format7zR/makefile10
-rwxr-xr-xCPP/7zip/Bundles/SFXCon/Main.cpp31
-rwxr-xr-xCPP/7zip/Bundles/SFXCon/SFXCon.dsp25
-rwxr-xr-xCPP/7zip/Bundles/SFXCon/makefile8
-rwxr-xr-xCPP/7zip/Bundles/SFXSetup/ExtractCallback.cpp6
-rwxr-xr-xCPP/7zip/Bundles/SFXSetup/ExtractEngine.cpp12
-rwxr-xr-xCPP/7zip/Bundles/SFXSetup/Main.cpp13
-rwxr-xr-xCPP/7zip/Bundles/SFXWin/Main.cpp5
-rwxr-xr-xCPP/7zip/Bundles/SFXWin/SFXWin.dsp17
-rwxr-xr-xCPP/7zip/Bundles/SFXWin/makefile7
-rwxr-xr-xCPP/7zip/Common/CWrappers.cpp127
-rwxr-xr-xCPP/7zip/Common/CWrappers.h46
-rwxr-xr-xCPP/7zip/Common/FilePathAutoRename.cpp30
-rwxr-xr-xCPP/7zip/Common/FileStreams.cpp189
-rwxr-xr-xCPP/7zip/Common/FileStreams.h20
-rwxr-xr-xCPP/7zip/Common/FilterCoder.cpp7
-rwxr-xr-xCPP/7zip/Common/InBuffer.cpp7
-rwxr-xr-xCPP/7zip/Common/InMemStream.h7
-rwxr-xr-xCPP/7zip/Common/LimitedStreams.cpp117
-rwxr-xr-xCPP/7zip/Common/LimitedStreams.h76
-rwxr-xr-xCPP/7zip/Common/MemBlocks.cpp4
-rwxr-xr-xCPP/7zip/Common/MemBlocks.h10
-rwxr-xr-xCPP/7zip/Common/MethodProps.cpp6
-rwxr-xr-xCPP/7zip/Common/OutBuffer.cpp9
-rwxr-xr-xCPP/7zip/Common/VirtThread.cpp3
-rwxr-xr-xCPP/7zip/Compress/BZip2Decoder.cpp70
-rwxr-xr-xCPP/7zip/Compress/BZip2Decoder.h38
-rwxr-xr-xCPP/7zip/Compress/BZip2Encoder.cpp5
-rwxr-xr-xCPP/7zip/Compress/BZip2Encoder.h7
-rwxr-xr-xCPP/7zip/Compress/Bcj2Coder.cpp3
-rwxr-xr-xCPP/7zip/Compress/BcjCoder.h3
-rwxr-xr-xCPP/7zip/Compress/BitlDecoder.h31
-rwxr-xr-xCPP/7zip/Compress/BitmDecoder.h6
-rwxr-xr-xCPP/7zip/Compress/BranchMisc.cpp3
-rwxr-xr-xCPP/7zip/Compress/ByteSwap.cpp37
-rwxr-xr-xCPP/7zip/Compress/ByteSwap.h30
-rwxr-xr-xCPP/7zip/Compress/ByteSwapRegister.cpp18
-rwxr-xr-xCPP/7zip/Compress/CodecExports.cpp5
-rwxr-xr-xCPP/7zip/Compress/CopyCoder.cpp21
-rwxr-xr-xCPP/7zip/Compress/CopyCoder.h4
-rwxr-xr-xCPP/7zip/Compress/DeflateDecoder.cpp82
-rwxr-xr-xCPP/7zip/Compress/DeflateDecoder.h45
-rwxr-xr-xCPP/7zip/Compress/DeflateEncoder.cpp3
-rwxr-xr-xCPP/7zip/Compress/DeflateEncoder.h5
-rwxr-xr-xCPP/7zip/Compress/DeltaFilter.cpp112
-rwxr-xr-xCPP/7zip/Compress/LZMA_Alone/AloneLZMA.dsp8
-rwxr-xr-xCPP/7zip/Compress/LZMA_Alone/LzmaAlone.cpp11
-rwxr-xr-xCPP/7zip/Compress/LZMA_Alone/LzmaBench.cpp17
-rwxr-xr-xCPP/7zip/Compress/LZMA_Alone/makefile1
-rwxr-xr-xCPP/7zip/Compress/Lzma2Decoder.cpp189
-rwxr-xr-xCPP/7zip/Compress/Lzma2Decoder.h73
-rwxr-xr-xCPP/7zip/Compress/Lzma2Encoder.cpp94
-rwxr-xr-xCPP/7zip/Compress/Lzma2Encoder.h36
-rwxr-xr-xCPP/7zip/Compress/Lzma2Register.cpp20
-rwxr-xr-xCPP/7zip/Compress/LzmaDecoder.cpp93
-rwxr-xr-xCPP/7zip/Compress/LzmaDecoder.h39
-rwxr-xr-xCPP/7zip/Compress/LzmaEncoder.cpp146
-rwxr-xr-xCPP/7zip/Compress/LzmaEncoder.h34
-rwxr-xr-xCPP/7zip/Compress/PpmdContext.h3
-rwxr-xr-xCPP/7zip/Compress/PpmdDecode.h3
-rwxr-xr-xCPP/7zip/Compress/PpmdDecoder.cpp1
-rwxr-xr-xCPP/7zip/Compress/PpmdDecoder.h1
-rwxr-xr-xCPP/7zip/Compress/PpmdEncode.h3
-rwxr-xr-xCPP/7zip/Compress/PpmdEncoder.cpp1
-rwxr-xr-xCPP/7zip/Compress/PpmdEncoder.h1
-rwxr-xr-xCPP/7zip/Compress/PpmdRegister.cpp1
-rwxr-xr-xCPP/7zip/Compress/PpmdSubAlloc.h6
-rwxr-xr-xCPP/7zip/Compress/PpmdType.h12
-rwxr-xr-xCPP/7zip/Compress/RangeCoder.h1
-rwxr-xr-xCPP/7zip/Compress/RangeCoderBit.h1
-rwxr-xr-xCPP/7zip/Compress/Rar3Vm.cpp3
-rwxr-xr-xCPP/7zip/Compress/ShrinkDecoder.cpp3
-rwxr-xr-xCPP/7zip/Compress/ZDecoder.cpp3
-rwxr-xr-xCPP/7zip/Crypto/7zAes.cpp5
-rwxr-xr-xCPP/7zip/Crypto/MyAes.h3
-rwxr-xr-xCPP/7zip/Crypto/Rar20Crypto.cpp9
-rwxr-xr-xCPP/7zip/Crypto/RarAes.h3
-rwxr-xr-xCPP/7zip/Crypto/Sha1.cpp6
-rwxr-xr-xCPP/7zip/Crypto/WzAes.h3
-rwxr-xr-xCPP/7zip/Crypto/ZipCrypto.cpp3
-rwxr-xr-xCPP/7zip/Crypto/ZipStrong.cpp3
-rwxr-xr-xCPP/7zip/Guid.txt23
-rwxr-xr-xCPP/7zip/ICoder.h33
-rwxr-xr-xCPP/7zip/MyVersion.h10
-rwxr-xr-xCPP/7zip/PropID.h8
-rwxr-xr-xCPP/7zip/UI/Agent/Agent.cpp136
-rwxr-xr-xCPP/7zip/UI/Agent/Agent.h28
-rwxr-xr-xCPP/7zip/UI/Agent/AgentOut.cpp45
-rwxr-xr-xCPP/7zip/UI/Agent/AgentProxy.cpp130
-rwxr-xr-xCPP/7zip/UI/Agent/AgentProxy.h26
-rwxr-xr-xCPP/7zip/UI/Agent/ArchiveFolder.cpp26
-rwxr-xr-xCPP/7zip/UI/Agent/ArchiveFolderOpen.cpp6
-rwxr-xr-xCPP/7zip/UI/Agent/ArchiveFolderOut.cpp37
-rwxr-xr-xCPP/7zip/UI/Agent/IFolderArchive.h13
-rwxr-xr-xCPP/7zip/UI/Agent/UpdateCallbackAgent.cpp16
-rwxr-xr-xCPP/7zip/UI/Client7z/Client7z.cpp8
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveCommandLine.cpp95
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveCommandLine.h1
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveExtractCallback.cpp180
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveExtractCallback.h106
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveName.cpp18
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveOpenCallback.cpp7
-rwxr-xr-xCPP/7zip/UI/Common/ArchiveOpenCallback.h8
-rwxr-xr-xCPP/7zip/UI/Common/CompressCall.cpp30
-rwxr-xr-xCPP/7zip/UI/Common/DirItem.h3
-rwxr-xr-xCPP/7zip/UI/Common/EnumDirItems.cpp12
-rwxr-xr-xCPP/7zip/UI/Common/Extract.cpp167
-rwxr-xr-xCPP/7zip/UI/Common/Extract.h29
-rwxr-xr-xCPP/7zip/UI/Common/ExtractingFilePath.cpp43
-rwxr-xr-xCPP/7zip/UI/Common/ExtractingFilePath.h7
-rwxr-xr-xCPP/7zip/UI/Common/LoadCodecs.cpp31
-rwxr-xr-xCPP/7zip/UI/Common/OpenArchive.cpp566
-rwxr-xr-xCPP/7zip/UI/Common/OpenArchive.h137
-rwxr-xr-xCPP/7zip/UI/Common/PropIDUtils.cpp87
-rwxr-xr-xCPP/7zip/UI/Common/PropIDUtils.h6
-rwxr-xr-xCPP/7zip/UI/Common/Update.cpp87
-rwxr-xr-xCPP/7zip/UI/Common/UpdateCallback.cpp21
-rwxr-xr-xCPP/7zip/UI/Common/UpdateCallback.h6
-rwxr-xr-xCPP/7zip/UI/Common/UpdatePair.cpp17
-rwxr-xr-xCPP/7zip/UI/Common/ZipRegistry.cpp8
-rwxr-xr-xCPP/7zip/UI/Console/Console.dsp20
-rwxr-xr-xCPP/7zip/UI/Console/List.cpp194
-rwxr-xr-xCPP/7zip/UI/Console/List.h1
-rwxr-xr-xCPP/7zip/UI/Console/Main.cpp50
-rwxr-xr-xCPP/7zip/UI/Console/UpdateCallbackConsole.cpp25
-rwxr-xr-xCPP/7zip/UI/Console/UpdateCallbackConsole.h9
-rwxr-xr-xCPP/7zip/UI/Console/UserInputUtils.cpp3
-rwxr-xr-xCPP/7zip/UI/Console/makefile7
-rwxr-xr-xCPP/7zip/UI/Explorer/ContextMenu.cpp92
-rwxr-xr-xCPP/7zip/UI/Explorer/Explorer.dsp8
-rwxr-xr-xCPP/7zip/UI/Explorer/makefile1
-rwxr-xr-xCPP/7zip/UI/Far/ExtractEngine.cpp14
-rwxr-xr-xCPP/7zip/UI/Far/ExtractEngine.h15
-rwxr-xr-xCPP/7zip/UI/Far/Far.dsp25
-rwxr-xr-xCPP/7zip/UI/Far/Main.cpp11
-rwxr-xr-xCPP/7zip/UI/Far/Messages.h11
-rwxr-xr-xCPP/7zip/UI/Far/Plugin.cpp18
-rwxr-xr-xCPP/7zip/UI/Far/Plugin.h1
-rwxr-xr-xCPP/7zip/UI/Far/PluginWrite.cpp4
-rwxr-xr-xCPP/7zip/UI/Far/UpdateCallback100.cpp12
-rwxr-xr-xCPP/7zip/UI/Far/UpdateCallback100.h13
-rwxr-xr-xCPP/7zip/UI/Far/makefile10
-rwxr-xr-xCPP/7zip/UI/FileManager/App.cpp41
-rwxr-xr-xCPP/7zip/UI/FileManager/App.h1
-rwxr-xr-xCPP/7zip/UI/FileManager/AppState.h6
-rwxr-xr-xCPP/7zip/UI/FileManager/ExtractCallback.cpp29
-rwxr-xr-xCPP/7zip/UI/FileManager/FM.cpp36
-rwxr-xr-xCPP/7zip/UI/FileManager/FM.dsp34
-rwxr-xr-xCPP/7zip/UI/FileManager/FSDrives.cpp309
-rwxr-xr-xCPP/7zip/UI/FileManager/FSDrives.h38
-rwxr-xr-xCPP/7zip/UI/FileManager/FSFolder.cpp34
-rwxr-xr-xCPP/7zip/UI/FileManager/FSFolder.h7
-rwxr-xr-xCPP/7zip/UI/FileManager/FSFolderCopy.cpp13
-rwxr-xr-xCPP/7zip/UI/FileManager/FileFolderPluginOpen.cpp35
-rwxr-xr-xCPP/7zip/UI/FileManager/FileFolderPluginOpen.h6
-rwxr-xr-xCPP/7zip/UI/FileManager/IFolder.h18
-rwxr-xr-xCPP/7zip/UI/FileManager/LangPage.rc4
-rwxr-xr-xCPP/7zip/UI/FileManager/LangUtils.cpp3
-rwxr-xr-xCPP/7zip/UI/FileManager/ListViewDialog.cpp3
-rwxr-xr-xCPP/7zip/UI/FileManager/MyLoadMenu.cpp25
-rwxr-xr-xCPP/7zip/UI/FileManager/NetFolder.cpp31
-rwxr-xr-xCPP/7zip/UI/FileManager/NetFolder.h25
-rwxr-xr-xCPP/7zip/UI/FileManager/OpenCallback.cpp36
-rwxr-xr-xCPP/7zip/UI/FileManager/OpenCallback.h22
-rwxr-xr-xCPP/7zip/UI/FileManager/Panel.cpp45
-rwxr-xr-xCPP/7zip/UI/FileManager/Panel.h56
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelCrc.cpp39
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelDrag.cpp2
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelFolderChange.cpp26
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelItemOpen.cpp255
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelItems.cpp135
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelListNotify.cpp33
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelMenu.cpp30
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelOperations.cpp16
-rwxr-xr-xCPP/7zip/UI/FileManager/PanelSplitFile.cpp25
-rwxr-xr-xCPP/7zip/UI/FileManager/PhysDriveFolder.cpp22
-rwxr-xr-xCPP/7zip/UI/FileManager/PhysDriveFolder.h7
-rwxr-xr-xCPP/7zip/UI/FileManager/ProgressDialog2.cpp36
-rwxr-xr-xCPP/7zip/UI/FileManager/ProgressDialog2.h89
-rwxr-xr-xCPP/7zip/UI/FileManager/ProgressDialog2.rc4
-rwxr-xr-xCPP/7zip/UI/FileManager/PropertyName.cpp120
-rwxr-xr-xCPP/7zip/UI/FileManager/PropertyName.rc96
-rwxr-xr-xCPP/7zip/UI/FileManager/PropertyNameRes.h96
-rwxr-xr-xCPP/7zip/UI/FileManager/RegistryAssociations.cpp11
-rwxr-xr-xCPP/7zip/UI/FileManager/RegistryUtils.cpp43
-rwxr-xr-xCPP/7zip/UI/FileManager/RegistryUtils.h17
-rwxr-xr-xCPP/7zip/UI/FileManager/RootFolder.cpp67
-rwxr-xr-xCPP/7zip/UI/FileManager/RootFolder.h25
-rwxr-xr-xCPP/7zip/UI/FileManager/SysIconUtils.cpp5
-rwxr-xr-xCPP/7zip/UI/FileManager/SystemPage.cpp2
-rwxr-xr-xCPP/7zip/UI/FileManager/SystemPage.rc7
-rwxr-xr-xCPP/7zip/UI/FileManager/TextPairs.cpp46
-rwxr-xr-xCPP/7zip/UI/FileManager/TextPairs.h6
-rwxr-xr-xCPP/7zip/UI/FileManager/UpdateCallback100.cpp33
-rwxr-xr-xCPP/7zip/UI/FileManager/ViewSettings.cpp4
-rwxr-xr-xCPP/7zip/UI/FileManager/makefile9
-rwxr-xr-xCPP/7zip/UI/FileManager/resource.h13
-rwxr-xr-xCPP/7zip/UI/FileManager/resource.rc13
-rwxr-xr-xCPP/7zip/UI/GUI/CompressDialog.cpp142
-rwxr-xr-xCPP/7zip/UI/GUI/CompressDialog.h19
-rwxr-xr-xCPP/7zip/UI/GUI/CompressDialog.rc2
-rwxr-xr-xCPP/7zip/UI/GUI/ExtractGUI.cpp25
-rwxr-xr-xCPP/7zip/UI/GUI/GUI.cpp32
-rwxr-xr-xCPP/7zip/UI/GUI/GUI.dsp76
-rwxr-xr-xCPP/7zip/UI/GUI/UpdateCallbackGUI.cpp15
-rwxr-xr-xCPP/7zip/UI/GUI/UpdateGUI.cpp22
-rwxr-xr-xCPP/7zip/UI/GUI/makefile7
-rwxr-xr-xCPP/Common/CRC.cpp3
-rwxr-xr-xCPP/Common/IntToString.cpp3
-rwxr-xr-xCPP/Common/IntToString.h8
-rwxr-xr-xCPP/Common/MyXml.cpp28
-rwxr-xr-xCPP/Common/StdInStream.cpp25
-rwxr-xr-xCPP/Common/StdInStream.h3
-rwxr-xr-xCPP/Common/StdOutStream.cpp21
-rwxr-xr-xCPP/Common/Types.h3
-rwxr-xr-xCPP/Windows/FileDevice.cpp49
-rwxr-xr-xCPP/Windows/FileDevice.h123
-rwxr-xr-xCPP/Windows/FileDir.cpp40
-rwxr-xr-xCPP/Windows/FileFind.cpp184
-rwxr-xr-xCPP/Windows/FileFind.h26
-rwxr-xr-xCPP/Windows/FileIO.cpp118
-rwxr-xr-xCPP/Windows/FileIO.h65
-rwxr-xr-xCPP/Windows/PropVariant.cpp20
-rwxr-xr-xCPP/Windows/PropVariant.h1
-rwxr-xr-xCPP/Windows/Security.cpp3
-rwxr-xr-xCPP/Windows/Synchronization.h19
-rwxr-xr-xCPP/Windows/Thread.h23
376 files changed, 15487 insertions, 9507 deletions
diff --git a/CPP/7zip/Archive/7z/7z.dsp b/CPP/7zip/Archive/7z/7z.dsp
index bddb2673..cf7aa975 100755
--- a/CPP/7zip/Archive/7z/7z.dsp
+++ b/CPP/7zip/Archive/7z/7z.dsp
@@ -598,11 +598,11 @@ SOURCE=..\..\..\Windows\Thread.h
# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Compress\Copy\CopyCoder.cpp
+SOURCE=..\..\Compress\CopyCoder.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\Copy\CopyCoder.h
+SOURCE=..\..\Compress\CopyCoder.h
# End Source File
# End Group
# Begin Group "C"
diff --git a/CPP/7zip/Archive/7z/7zEncode.cpp b/CPP/7zip/Archive/7z/7zEncode.cpp
index 01803842..c97f893b 100755
--- a/CPP/7zip/Archive/7z/7zEncode.cpp
+++ b/CPP/7zip/Archive/7z/7zEncode.cpp
@@ -1,21 +1,21 @@
-// Encode.cpp
+// 7zEncode.cpp
#include "StdAfx.h"
-#include "7zEncode.h"
-#include "7zSpecStream.h"
-
-#include "../../IPassword.h"
-#include "../../Common/ProgressUtils.h"
+#include "../../Common/CreateCoder.h"
+#include "../../Common/FilterCoder.h"
#include "../../Common/LimitedStreams.h"
#include "../../Common/InOutTempBuffer.h"
+#include "../../Common/ProgressUtils.h"
#include "../../Common/StreamObjects.h"
-#include "../../Common/CreateCoder.h"
-#include "../../Common/FilterCoder.h"
-static const UInt64 k_AES = 0x06F10701;
-static const UInt64 k_BCJ = 0x03030103;
+#include "7zEncode.h"
+#include "7zSpecStream.h"
+
+static const UInt64 k_Delta = 0x03;
+static const UInt64 k_BCJ = 0x03030103;
static const UInt64 k_BCJ2 = 0x0303011B;
+static const UInt64 k_AES = 0x06F10701;
namespace NArchive {
namespace N7z {
@@ -240,10 +240,10 @@ HRESULT CEncoder::Encode(
UInt32 progressIndex = mainCoderIndex;
- for (i = 0; i < _codersInfo.Size(); i++)
+ for (i = 0; i + 1 < _codersInfo.Size(); i++)
{
- const CCoderInfo &e = _codersInfo[i];
- if ((e.MethodID == k_BCJ || e.MethodID == k_BCJ2) && i + 1 < _codersInfo.Size())
+ UInt64 m = _codersInfo[i].MethodID;
+ if (m == k_Delta || m == k_BCJ || m == k_BCJ2)
progressIndex = i + 1;
}
diff --git a/CPP/7zip/Archive/7z/7zFolderOutStream.cpp b/CPP/7zip/Archive/7z/7zFolderOutStream.cpp
index 61b938d0..75505863 100755
--- a/CPP/7zip/Archive/7z/7zFolderOutStream.cpp
+++ b/CPP/7zip/Archive/7z/7zFolderOutStream.cpp
@@ -9,156 +9,132 @@ namespace N7z {
CFolderOutStream::CFolderOutStream()
{
- _outStreamWithHashSpec = new COutStreamWithCRC;
- _outStreamWithHash = _outStreamWithHashSpec;
+ _crcStreamSpec = new COutStreamWithCRC;
+ _crcStream = _crcStreamSpec;
}
HRESULT CFolderOutStream::Init(
const CArchiveDatabaseEx *archiveDatabase,
- UInt32 ref2Offset,
- UInt32 startIndex,
+ UInt32 ref2Offset, UInt32 startIndex,
const CBoolVector *extractStatuses,
IArchiveExtractCallback *extractCallback,
- bool testMode,
- bool checkCrc)
+ bool testMode, bool checkCrc)
{
- _archiveDatabase = archiveDatabase;
+ _db = archiveDatabase;
_ref2Offset = ref2Offset;
_startIndex = startIndex;
_extractStatuses = extractStatuses;
_extractCallback = extractCallback;
_testMode = testMode;
-
_checkCrc = checkCrc;
_currentIndex = 0;
_fileIsOpen = false;
- return WriteEmptyFiles();
+ return ProcessEmptyFiles();
}
HRESULT CFolderOutStream::OpenFile()
{
- Int32 askMode;
- if((*_extractStatuses)[_currentIndex])
- askMode = _testMode ?
- NArchive::NExtract::NAskMode::kTest :
- NArchive::NExtract::NAskMode::kExtract;
- else
- askMode = NArchive::NExtract::NAskMode::kSkip;
+ Int32 askMode = ((*_extractStatuses)[_currentIndex]) ? (_testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract):
+ NArchive::NExtract::NAskMode::kSkip;
CMyComPtr<ISequentialOutStream> realOutStream;
-
UInt32 index = _startIndex + _currentIndex;
RINOK(_extractCallback->GetStream(_ref2Offset + index, &realOutStream, askMode));
-
- _outStreamWithHashSpec->SetStream(realOutStream);
- _outStreamWithHashSpec->Init(_checkCrc);
- if (askMode == NArchive::NExtract::NAskMode::kExtract &&
- (!realOutStream))
- {
- const CFileItem &fi = _archiveDatabase->Files[index];
- if (!_archiveDatabase->IsItemAnti(index) && !fi.IsDir)
- askMode = NArchive::NExtract::NAskMode::kSkip;
- }
+ _crcStreamSpec->SetStream(realOutStream);
+ _crcStreamSpec->Init(_checkCrc);
+ _fileIsOpen = true;
+ const CFileItem &fi = _db->Files[index];
+ _rem = fi.Size;
+ if (askMode == NArchive::NExtract::NAskMode::kExtract && !realOutStream &&
+ !_db->IsItemAnti(index) && !fi.IsDir)
+ askMode = NArchive::NExtract::NAskMode::kSkip;
return _extractCallback->PrepareOperation(askMode);
}
-HRESULT CFolderOutStream::WriteEmptyFiles()
+HRESULT CFolderOutStream::CloseFileAndSetResult(Int32 res)
+{
+ _crcStreamSpec->ReleaseStream();
+ _fileIsOpen = false;
+ _currentIndex++;
+ return _extractCallback->SetOperationResult(res);
+}
+
+HRESULT CFolderOutStream::CloseFileAndSetResult()
+{
+ const CFileItem &fi = _db->Files[_startIndex + _currentIndex];
+ return CloseFileAndSetResult(
+ (fi.IsDir || !fi.CrcDefined || !_checkCrc || fi.Crc == _crcStreamSpec->GetCRC()) ?
+ NArchive::NExtract::NOperationResult::kOK :
+ NArchive::NExtract::NOperationResult::kCRCError);
+}
+
+HRESULT CFolderOutStream::ProcessEmptyFiles()
{
- for(;_currentIndex < _extractStatuses->Size(); _currentIndex++)
+ while (_currentIndex < _extractStatuses->Size() && _db->Files[_startIndex + _currentIndex].Size == 0)
{
- UInt32 index = _startIndex + _currentIndex;
- const CFileItem &fi = _archiveDatabase->Files[index];
- if (!_archiveDatabase->IsItemAnti(index) && !fi.IsDir && fi.Size != 0)
- return S_OK;
RINOK(OpenFile());
- RINOK(_extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
- _outStreamWithHashSpec->ReleaseStream();
+ RINOK(CloseFileAndSetResult());
}
return S_OK;
}
-STDMETHODIMP CFolderOutStream::Write(const void *data,
- UInt32 size, UInt32 *processedSize)
+STDMETHODIMP CFolderOutStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
- UInt32 realProcessedSize = 0;
- while(_currentIndex < _extractStatuses->Size())
+ if (processedSize != NULL)
+ *processedSize = 0;
+ while (size != 0)
{
if (_fileIsOpen)
{
- UInt32 index = _startIndex + _currentIndex;
- const CFileItem &fi = _archiveDatabase->Files[index];
- UInt64 fileSize = fi.Size;
-
- UInt32 numBytesToWrite = (UInt32)MyMin(fileSize - _filePos,
- UInt64(size - realProcessedSize));
-
- UInt32 processedSizeLocal;
- RINOK(_outStreamWithHash->Write((const Byte *)data + realProcessedSize,
- numBytesToWrite, &processedSizeLocal));
-
- _filePos += processedSizeLocal;
- realProcessedSize += processedSizeLocal;
- if (_filePos == fileSize)
+ UInt32 cur = size < _rem ? size : (UInt32)_rem;
+ RINOK(_crcStream->Write(data, cur, &cur));
+ if (cur == 0)
+ break;
+ data = (const Byte *)data + cur;
+ size -= cur;
+ _rem -= cur;
+ if (processedSize != NULL)
+ *processedSize += cur;
+ if (_rem == 0)
{
- bool digestsAreEqual;
- if (fi.CrcDefined && _checkCrc)
- digestsAreEqual = fi.Crc == _outStreamWithHashSpec->GetCRC();
- else
- digestsAreEqual = true;
-
- RINOK(_extractCallback->SetOperationResult(
- digestsAreEqual ?
- NArchive::NExtract::NOperationResult::kOK :
- NArchive::NExtract::NOperationResult::kCRCError));
- _outStreamWithHashSpec->ReleaseStream();
- _fileIsOpen = false;
- _currentIndex++;
- }
- if (realProcessedSize == size)
- {
- if (processedSize != NULL)
- *processedSize = realProcessedSize;
- return WriteEmptyFiles();
+ RINOK(CloseFileAndSetResult());
+ RINOK(ProcessEmptyFiles());
+ continue;
}
}
else
{
+ RINOK(ProcessEmptyFiles());
+ if (_currentIndex == _extractStatuses->Size())
+ {
+ // we support partial extracting
+ if (processedSize != NULL)
+ *processedSize += size;
+ break;
+ }
RINOK(OpenFile());
- _fileIsOpen = true;
- _filePos = 0;
}
}
- if (processedSize != NULL)
- *processedSize = size;
return S_OK;
}
HRESULT CFolderOutStream::FlushCorrupted(Int32 resultEOperationResult)
{
- while(_currentIndex < _extractStatuses->Size())
+ while (_currentIndex < _extractStatuses->Size())
{
if (_fileIsOpen)
{
- RINOK(_extractCallback->SetOperationResult(resultEOperationResult));
- _outStreamWithHashSpec->ReleaseStream();
- _fileIsOpen = false;
- _currentIndex++;
+ RINOK(CloseFileAndSetResult(resultEOperationResult));
}
else
{
RINOK(OpenFile());
- _fileIsOpen = true;
}
}
return S_OK;
}
-HRESULT CFolderOutStream::WasWritingFinished()
-{
- if (_currentIndex == _extractStatuses->Size())
- return S_OK;
- return E_FAIL;
-}
-
}}
diff --git a/CPP/7zip/Archive/7z/7zFolderOutStream.h b/CPP/7zip/Archive/7z/7zFolderOutStream.h
index f54fba3e..e6e05b85 100755
--- a/CPP/7zip/Archive/7z/7zFolderOutStream.h
+++ b/CPP/7zip/Archive/7z/7zFolderOutStream.h
@@ -1,7 +1,7 @@
// 7zFolderOutStream.h
-#ifndef __7Z_FOLDEROUTSTREAM_H
-#define __7Z_FOLDEROUTSTREAM_H
+#ifndef __7Z_FOLDER_OUT_STREAM_H
+#define __7Z_FOLDER_OUT_STREAM_H
#include "7zIn.h"
@@ -16,43 +16,39 @@ class CFolderOutStream:
public ISequentialOutStream,
public CMyUnknownImp
{
-public:
- MY_UNKNOWN_IMP
-
- CFolderOutStream();
-
- STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
-private:
-
- COutStreamWithCRC *_outStreamWithHashSpec;
- CMyComPtr<ISequentialOutStream> _outStreamWithHash;
- const CArchiveDatabaseEx *_archiveDatabase;
+ COutStreamWithCRC *_crcStreamSpec;
+ CMyComPtr<ISequentialOutStream> _crcStream;
+ const CArchiveDatabaseEx *_db;
const CBoolVector *_extractStatuses;
- UInt32 _startIndex;
+ CMyComPtr<IArchiveExtractCallback> _extractCallback;
UInt32 _ref2Offset;
+ UInt32 _startIndex;
int _currentIndex;
- // UInt64 _currentDataPos;
- CMyComPtr<IArchiveExtractCallback> _extractCallback;
bool _testMode;
-
- bool _fileIsOpen;
-
bool _checkCrc;
- UInt64 _filePos;
+ bool _fileIsOpen;
+ UInt64 _rem;
HRESULT OpenFile();
- HRESULT WriteEmptyFiles();
+ HRESULT CloseFileAndSetResult(Int32 res);
+ HRESULT CloseFileAndSetResult();
+ HRESULT ProcessEmptyFiles();
public:
+ MY_UNKNOWN_IMP
+
+ CFolderOutStream();
+
+ STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
+
HRESULT Init(
const CArchiveDatabaseEx *archiveDatabase,
- UInt32 ref2Offset,
- UInt32 startIndex,
+ UInt32 ref2Offset, UInt32 startIndex,
const CBoolVector *extractStatuses,
IArchiveExtractCallback *extractCallback,
- bool testMode,
- bool checkCrc);
+ bool testMode, bool checkCrc);
HRESULT FlushCorrupted(Int32 resultEOperationResult);
- HRESULT WasWritingFinished();
+ HRESULT WasWritingFinished() const
+ { return (_currentIndex == _extractStatuses->Size()) ? S_OK: E_FAIL; }
};
}}
diff --git a/CPP/7zip/Archive/7z/7zHandler.cpp b/CPP/7zip/Archive/7z/7zHandler.cpp
index 44131fae..6f0cf6b2 100755
--- a/CPP/7zip/Archive/7z/7zHandler.cpp
+++ b/CPP/7zip/Archive/7z/7zHandler.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
- #include "../../../../C/CpuArch.h"
-}
+#include "../../../../C/CpuArch.h"
#include "../../../Common/ComTry.h"
#include "../../../Common/IntToString.h"
@@ -176,6 +173,8 @@ static UString GetStringForSizeValue(UInt32 value)
}
static const UInt64 k_Copy = 0x0;
+static const UInt64 k_Delta = 3;
+static const UInt64 k_LZMA2 = 0x21;
static const UInt64 k_LZMA = 0x030101;
static const UInt64 k_PPMD = 0x030401;
@@ -183,12 +182,10 @@ static wchar_t GetHex(Byte value)
{
return (wchar_t)((value < 10) ? (L'0' + value) : (L'A' + (value - 10)));
}
-static inline UString GetHex2(Byte value)
+static inline void AddHexToString(UString &res, Byte value)
{
- UString result;
- result += GetHex((Byte)(value >> 4));
- result += GetHex((Byte)(value & 0xF));
- return result;
+ res += GetHex((Byte)(value >> 4));
+ res += GetHex((Byte)(value & 0xF));
}
#endif
@@ -273,89 +270,82 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *va
UString methodsString;
for (int i = folderInfo.Coders.Size() - 1; i >= 0; i--)
{
- const CCoderInfo &coderInfo = folderInfo.Coders[i];
+ const CCoderInfo &coder = folderInfo.Coders[i];
if (!methodsString.IsEmpty())
methodsString += L' ';
+ UString methodName, propsString;
+ bool methodIsKnown = FindMethod(
+ EXTERNAL_CODECS_VARS
+ coder.MethodID, methodName);
+
+ if (!methodIsKnown)
+ methodsString += ConvertMethodIdToString(coder.MethodID);
+ else
{
- UString methodName;
- bool methodIsKnown = FindMethod(
- EXTERNAL_CODECS_VARS
- coderInfo.MethodID, methodName);
-
- if (methodIsKnown)
+ methodsString += methodName;
+ if (coder.MethodID == k_Delta && coder.Props.GetCapacity() == 1)
+ propsString = ConvertUInt32ToString((UInt32)coder.Props[0] + 1);
+ else if (coder.MethodID == k_LZMA && coder.Props.GetCapacity() == 5)
{
- methodsString += methodName;
- if (coderInfo.MethodID == k_LZMA)
- {
- if (coderInfo.Props.GetCapacity() >= 5)
- {
- methodsString += L":";
- UInt32 dicSize = GetUi32((const Byte *)coderInfo.Props + 1);
- methodsString += GetStringForSizeValue(dicSize);
- }
- }
- else if (coderInfo.MethodID == k_PPMD)
+ UInt32 dicSize = GetUi32((const Byte *)coder.Props + 1);
+ propsString = GetStringForSizeValue(dicSize);
+ }
+ else if (coder.MethodID == k_LZMA2 && coder.Props.GetCapacity() == 1)
+ {
+ Byte p = coder.Props[0];
+ UInt32 dicSize = (((UInt32)2 | ((p) & 1)) << ((p) / 2 + 11));
+ propsString = GetStringForSizeValue(dicSize);
+ }
+ else if (coder.MethodID == k_PPMD && coder.Props.GetCapacity() == 5)
+ {
+ Byte order = *(const Byte *)coder.Props;
+ methodsString += L'o';
+ methodsString += ConvertUInt32ToString(order);
+ methodsString += L":mem";
+ UInt32 dicSize = GetUi32((const Byte *)coder.Props + 1);
+ propsString = GetStringForSizeValue(dicSize);
+ }
+ else if (coder.MethodID == k_AES && coder.Props.GetCapacity() >= 1)
+ {
+ const Byte *data = (const Byte *)coder.Props;
+ Byte firstByte = *data++;
+ UInt32 numCyclesPower = firstByte & 0x3F;
+ propsString = ConvertUInt32ToString(numCyclesPower);
+ /*
+ if ((firstByte & 0xC0) != 0)
{
- if (coderInfo.Props.GetCapacity() >= 5)
+ UInt32 saltSize = (firstByte >> 7) & 1;
+ UInt32 ivSize = (firstByte >> 6) & 1;
+ if (coder.Props.GetCapacity() >= 2)
{
- Byte order = *(const Byte *)coderInfo.Props;
- methodsString += L":o";
- methodsString += ConvertUInt32ToString(order);
- methodsString += L":mem";
- UInt32 dicSize = GetUi32((const Byte *)coderInfo.Props + 1);
- methodsString += GetStringForSizeValue(dicSize);
+ Byte secondByte = *data++;
+ saltSize += (secondByte >> 4);
+ ivSize += (secondByte & 0x0F);
}
}
- else if (coderInfo.MethodID == k_AES)
+ */
+ }
+ }
+ if (!propsString.IsEmpty())
+ {
+ methodsString += L':';
+ methodsString += propsString;
+ }
+ else if (coder.Props.GetCapacity() > 0)
+ {
+ methodsString += L":[";
+ for (size_t bi = 0; bi < coder.Props.GetCapacity(); bi++)
+ {
+ if (bi > 5 && bi + 1 < coder.Props.GetCapacity())
{
- if (coderInfo.Props.GetCapacity() >= 1)
- {
- methodsString += L":";
- const Byte *data = (const Byte *)coderInfo.Props;
- Byte firstByte = *data++;
- UInt32 numCyclesPower = firstByte & 0x3F;
- methodsString += ConvertUInt32ToString(numCyclesPower);
- /*
- if ((firstByte & 0xC0) != 0)
- {
- methodsString += L":";
- return S_OK;
- UInt32 saltSize = (firstByte >> 7) & 1;
- UInt32 ivSize = (firstByte >> 6) & 1;
- if (coderInfo.Props.GetCapacity() >= 2)
- {
- Byte secondByte = *data++;
- saltSize += (secondByte >> 4);
- ivSize += (secondByte & 0x0F);
- }
- }
- */
- }
+ methodsString += L"..";
+ break;
}
else
- {
- if (coderInfo.Props.GetCapacity() > 0)
- {
- methodsString += L":[";
- for (size_t bi = 0; bi < coderInfo.Props.GetCapacity(); bi++)
- {
- if (bi > 5 && bi + 1 < coderInfo.Props.GetCapacity())
- {
- methodsString += L"..";
- break;
- }
- else
- methodsString += GetHex2(coderInfo.Props[bi]);
- }
- methodsString += L"]";
- }
- }
- }
- else
- {
- methodsString += ConvertMethodIdToString(coderInfo.MethodID);
+ AddHexToString(methodsString, coder.Props[bi]);
}
+ methodsString += L']';
}
}
prop = methodsString;
diff --git a/CPP/7zip/Archive/7z/7zHandler.h b/CPP/7zip/Archive/7z/7zHandler.h
index 9adf8464..68fb034f 100755
--- a/CPP/7zip/Archive/7z/7zHandler.h
+++ b/CPP/7zip/Archive/7z/7zHandler.h
@@ -5,9 +5,6 @@
#include "../../ICoder.h"
#include "../IArchive.h"
-#include "7zIn.h"
-
-#include "7zCompressionMode.h"
#include "../../Common/CreateCoder.h"
@@ -15,6 +12,9 @@
#include "../Common/HandlerOut.h"
#endif
+#include "7zCompressionMode.h"
+#include "7zIn.h"
+
namespace NArchive {
namespace N7z {
@@ -90,8 +90,6 @@ private:
CRecordVector<CBind> _binds;
- HRESULT SetPassword(CCompressionMethodMode &methodMode, IArchiveUpdateCallback *updateCallback);
-
HRESULT SetCompressionMethod(CCompressionMethodMode &method,
CObjectVector<COneMethodInfo> &methodsInfo
#ifdef COMPRESS_MT
diff --git a/CPP/7zip/Archive/7z/7zHandlerOut.cpp b/CPP/7zip/Archive/7z/7zHandlerOut.cpp
index 3e2591d5..e2c250ab 100755
--- a/CPP/7zip/Archive/7z/7zHandlerOut.cpp
+++ b/CPP/7zip/Archive/7z/7zHandlerOut.cpp
@@ -40,31 +40,6 @@ STDMETHODIMP CHandler::GetFileTimeType(UInt32 *type)
return S_OK;
}
-HRESULT CHandler::SetPassword(CCompressionMethodMode &methodMode,
- IArchiveUpdateCallback *updateCallback)
-{
- CMyComPtr<ICryptoGetTextPassword2> getTextPassword;
- if (!getTextPassword)
- {
- CMyComPtr<IArchiveUpdateCallback> udateCallback2(updateCallback);
- udateCallback2.QueryInterface(IID_ICryptoGetTextPassword2, &getTextPassword);
- }
-
- if (getTextPassword)
- {
- CMyComBSTR password;
- Int32 passwordIsDefined;
- RINOK(getTextPassword->CryptoGetTextPassword2(
- &passwordIsDefined, &password));
- methodMode.PasswordIsDefined = IntToBool(passwordIsDefined);
- if (methodMode.PasswordIsDefined)
- methodMode.Password = password;
- }
- else
- methodMode.PasswordIsDefined = false;
- return S_OK;
-}
-
HRESULT CHandler::SetCompressionMethod(
CCompressionMethodMode &methodMode,
CCompressionMethodMode &headerMethod)
@@ -210,7 +185,7 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
const CArchiveDatabaseEx *db = 0;
#ifdef _7Z_VOL
- if(_volumes.Size() > 1)
+ if (_volumes.Size() > 1)
return E_FAIL;
const CVolume *volume = 0;
if (_volumes.Size() == 1)
@@ -227,14 +202,13 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
for (UInt32 i = 0; i < numItems; i++)
{
- Int32 newData;
- Int32 newProperties;
+ Int32 newData, newProps;
UInt32 indexInArchive;
if (!updateCallback)
return E_FAIL;
- RINOK(updateCallback->GetUpdateItemInfo(i, &newData, &newProperties, &indexInArchive));
+ RINOK(updateCallback->GetUpdateItemInfo(i, &newData, &newProps, &indexInArchive));
CUpdateItem ui;
- ui.NewProperties = IntToBool(newProperties);
+ ui.NewProps = IntToBool(newProps);
ui.NewData = IntToBool(newData);
ui.IndexInArchive = indexInArchive;
ui.IndexInClient = i;
@@ -243,6 +217,8 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
if (ui.IndexInArchive != -1)
{
+ if (db == 0 || ui.IndexInArchive >= db->Files.Size())
+ return E_INVALIDARG;
const CFileItem &fi = db->Files[ui.IndexInArchive];
ui.Name = fi.Name;
ui.IsDir = fi.IsDir;
@@ -254,7 +230,7 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
ui.MTimeDefined = db->MTime.GetItem(ui.IndexInArchive, ui.MTime);
}
- if (ui.NewProperties)
+ if (ui.NewProps)
{
bool nameIsDefined;
bool folderStatusIsDefined;
@@ -350,7 +326,20 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
headerMethod.NumThreads = 1;
#endif
- RINOK(SetPassword(methodMode, updateCallback));
+ CMyComPtr<ICryptoGetTextPassword2> getPassword2;
+ updateCallback->QueryInterface(IID_ICryptoGetTextPassword2, (void **)&getPassword2);
+
+ if (getPassword2)
+ {
+ CMyComBSTR password;
+ Int32 passwordIsDefined;
+ RINOK(getPassword2->CryptoGetTextPassword2(&passwordIsDefined, &password));
+ methodMode.PasswordIsDefined = IntToBool(passwordIsDefined);
+ if (methodMode.PasswordIsDefined)
+ methodMode.Password = password;
+ }
+ else
+ methodMode.PasswordIsDefined = false;
bool compressMainHeader = _compressHeaders; // check it
@@ -365,8 +354,11 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
encryptHeaders = _passwordIsDefined;
#endif
compressMainHeader = true;
- if(encryptHeaders)
- RINOK(SetPassword(headerMethod, updateCallback));
+ if (encryptHeaders)
+ {
+ headerMethod.PasswordIsDefined = methodMode.PasswordIsDefined;
+ headerMethod.Password = methodMode.Password;
+ }
}
if (numItems < 2)
@@ -391,6 +383,10 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
COutArchive archive;
CArchiveDatabase newDatabase;
+
+ CMyComPtr<ICryptoGetTextPassword> getPassword;
+ updateCallback->QueryInterface(IID_ICryptoGetTextPassword, (void **)&getPassword);
+
HRESULT res = Update(
EXTERNAL_CODECS_VARS
#ifdef _7Z_VOL
@@ -401,7 +397,11 @@ STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numIt
db,
#endif
updateItems,
- archive, newDatabase, outStream, updateCallback, options);
+ archive, newDatabase, outStream, updateCallback, options
+ #ifndef _NO_CRYPTO
+ , getPassword
+ #endif
+ );
RINOK(res);
diff --git a/CPP/7zip/Archive/7z/7zIn.cpp b/CPP/7zip/Archive/7z/7zIn.cpp
index ab78eeae..f1458e0c 100755
--- a/CPP/7zip/Archive/7z/7zIn.cpp
+++ b/CPP/7zip/Archive/7z/7zIn.cpp
@@ -2,11 +2,8 @@
#include "StdAfx.h"
-extern "C"
-{
- #include "../../../../C/7zCrc.h"
- #include "../../../../C/CpuArch.h"
-}
+#include "../../../../C/7zCrc.h"
+#include "../../../../C/CpuArch.h"
#include "../../Common/StreamObjects.h"
#include "../../Common/StreamUtils.h"
@@ -198,16 +195,16 @@ void CInByte2::ReadBytes(Byte *data, size_t size)
data[i] = _buffer[_pos++];
}
-void CInByte2::SkeepData(UInt64 size)
+void CInByte2::SkipData(UInt64 size)
{
if (size > _size - _pos)
ThrowEndOfData();
_pos += (size_t)size;
}
-void CInByte2::SkeepData()
+void CInByte2::SkipData()
{
- SkeepData(ReadNumber());
+ SkipData(ReadNumber());
}
UInt64 CInByte2::ReadNumber()
@@ -363,7 +360,7 @@ void CInArchive::ReadArchiveProperties(CInArchiveInfo & /* archiveInfo */)
{
if (ReadID() == NID::kEnd)
break;
- SkeepData();
+ SkipData();
}
}
@@ -456,7 +453,7 @@ void CInArchive::WaitAttribute(UInt64 attribute)
return;
if (type == NID::kEnd)
ThrowIncorrect();
- SkeepData();
+ SkipData();
}
}
@@ -502,7 +499,7 @@ void CInArchive::ReadPackInfo(
ReadHashDigests(numPackStreams, packCRCsDefined, packCRCs);
continue;
}
- SkeepData();
+ SkipData();
}
if (packCRCsDefined.IsEmpty())
{
@@ -563,7 +560,7 @@ void CInArchive::ReadUnpackInfo(
}
continue;
}
- SkeepData();
+ SkipData();
}
}
@@ -590,7 +587,7 @@ void CInArchive::ReadSubStreamsInfo(
break;
if (type == NID::kEnd)
break;
- SkeepData();
+ SkipData();
}
if (numUnpackStreamsInFolders.IsEmpty())
@@ -665,7 +662,7 @@ void CInArchive::ReadSubStreamsInfo(
return;
}
else
- SkeepData();
+ SkipData();
type = ReadID();
}
}
@@ -1006,7 +1003,7 @@ HRESULT CInArchive::ReadHeader(
db.ArchiveInfo.FileInfoPopIDs.Add(type);
}
else
- SkeepData(size);
+ SkipData(size);
bool checkRecordsSize = (db.ArchiveInfo.Version.Major > 0 ||
db.ArchiveInfo.Version.Minor > 2);
if (checkRecordsSize && _inByteBack->_pos - ppp != size)
diff --git a/CPP/7zip/Archive/7z/7zIn.h b/CPP/7zip/Archive/7z/7zIn.h
index 09c51105..971f27b2 100755
--- a/CPP/7zip/Archive/7z/7zIn.h
+++ b/CPP/7zip/Archive/7z/7zIn.h
@@ -110,8 +110,8 @@ public:
}
Byte ReadByte();
void ReadBytes(Byte *data, size_t size);
- void SkeepData(UInt64 size);
- void SkeepData();
+ void SkipData(UInt64 size);
+ void SkipData();
UInt64 ReadNumber();
CNum ReadNum();
UInt32 ReadUInt32();
@@ -162,8 +162,8 @@ private:
UInt64 ReadID() { return _inByteBack->ReadNumber(); }
UInt32 ReadUInt32() { return _inByteBack->ReadUInt32(); }
UInt64 ReadUInt64() { return _inByteBack->ReadUInt64(); }
- void SkeepData(UInt64 size) { _inByteBack->SkeepData(size); }
- void SkeepData() { _inByteBack->SkeepData(); }
+ void SkipData(UInt64 size) { _inByteBack->SkipData(size); }
+ void SkipData() { _inByteBack->SkipData(); }
void WaitAttribute(UInt64 attribute);
void ReadArchiveProperties(CInArchiveInfo &archiveInfo);
diff --git a/CPP/7zip/Archive/7z/7zOut.cpp b/CPP/7zip/Archive/7z/7zOut.cpp
index 7ac3c18c..e897680e 100755
--- a/CPP/7zip/Archive/7z/7zOut.cpp
+++ b/CPP/7zip/Archive/7z/7zOut.cpp
@@ -2,16 +2,14 @@
#include "StdAfx.h"
+#include "../../../../C/7zCrc.h"
+
#include "../../../Common/AutoPtr.h"
+
#include "../../Common/StreamObjects.h"
#include "7zOut.h"
-extern "C"
-{
-#include "../../../../C/7zCrc.h"
-}
-
static HRESULT WriteBytes(ISequentialOutStream *stream, const void *data, size_t size)
{
while (size > 0)
@@ -141,7 +139,7 @@ void COutArchive::Close()
Stream.Release();
}
-HRESULT COutArchive::SkeepPrefixArchiveHeader()
+HRESULT COutArchive::SkipPrefixArchiveHeader()
{
#ifdef _7Z_VOL
if (_endMarker)
diff --git a/CPP/7zip/Archive/7z/7zOut.h b/CPP/7zip/Archive/7z/7zOut.h
index bdd84abc..9d8ef308 100755
--- a/CPP/7zip/Archive/7z/7zOut.h
+++ b/CPP/7zip/Archive/7z/7zOut.h
@@ -1,12 +1,12 @@
-// 7z/Out.h
+// 7zOut.h
#ifndef __7Z_OUT_H
#define __7Z_OUT_H
-#include "7zHeader.h"
-#include "7zItem.h"
#include "7zCompressionMode.h"
#include "7zEncode.h"
+#include "7zHeader.h"
+#include "7zItem.h"
#include "../../Common/OutBuffer.h"
@@ -137,7 +137,7 @@ public:
CMyComPtr<ISequentialOutStream> SeqStream;
HRESULT Create(ISequentialOutStream *stream, bool endMarker);
void Close();
- HRESULT SkeepPrefixArchiveHeader();
+ HRESULT SkipPrefixArchiveHeader();
HRESULT WriteDatabase(
DECL_EXTERNAL_CODECS_LOC_VARS
const CArchiveDatabase &db,
diff --git a/CPP/7zip/Archive/7z/7zUpdate.cpp b/CPP/7zip/Archive/7z/7zUpdate.cpp
index 0285b189..9506e8f7 100755
--- a/CPP/7zip/Archive/7z/7zUpdate.cpp
+++ b/CPP/7zip/Archive/7z/7zUpdate.cpp
@@ -5,10 +5,14 @@
#include "../../Common/LimitedStreams.h"
#include "../../Common/ProgressUtils.h"
+#include "../../Common/CreateCoder.h"
+
#include "../../Compress/CopyCoder.h"
#include "../Common/ItemNameUtils.h"
+#include "../Common/OutStreamWithCRC.h"
+#include "7zDecode.h"
#include "7zEncode.h"
#include "7zFolderInStream.h"
#include "7zHandler.h"
@@ -18,6 +22,11 @@
namespace NArchive {
namespace N7z {
+static const UInt64 k_LZMA = 0x030101;
+static const UInt64 k_BCJ = 0x03030103;
+static const UInt64 k_BCJ2 = 0x0303011B;
+static const UInt64 k_AES = 0x06F10701;
+
static const wchar_t *kMatchFinderForBCJ2_LZMA = L"BT2";
static const UInt32 kDictionaryForBCJ2_LZMA = 1 << 20;
static const UInt32 kAlgorithmForBCJ2_LZMA = 1;
@@ -64,27 +73,29 @@ UString CUpdateItem::GetExtension() const
#define RINOZ(x) { int __tt = (x); if (__tt != 0) return __tt; }
+#define RINOZ_COMP(a, b) RINOZ(MyCompare(a, b))
+
static int CompareBuffers(const CByteBuffer &a1, const CByteBuffer &a2)
{
size_t c1 = a1.GetCapacity();
size_t c2 = a2.GetCapacity();
- RINOZ(MyCompare(c1, c2));
+ RINOZ_COMP(c1, c2);
for (size_t i = 0; i < c1; i++)
- RINOZ(MyCompare(a1[i], a2[i]));
+ RINOZ_COMP(a1[i], a2[i]);
return 0;
}
static int CompareCoders(const CCoderInfo &c1, const CCoderInfo &c2)
{
- RINOZ(MyCompare(c1.NumInStreams, c2.NumInStreams));
- RINOZ(MyCompare(c1.NumOutStreams, c2.NumOutStreams));
- RINOZ(MyCompare(c1.MethodID, c2.MethodID));
+ RINOZ_COMP(c1.NumInStreams, c2.NumInStreams);
+ RINOZ_COMP(c1.NumOutStreams, c2.NumOutStreams);
+ RINOZ_COMP(c1.MethodID, c2.MethodID);
return CompareBuffers(c1.Props, c2.Props);
}
static int CompareBindPairs(const CBindPair &b1, const CBindPair &b2)
{
- RINOZ(MyCompare(b1.InIndex, b2.InIndex));
+ RINOZ_COMP(b1.InIndex, b2.InIndex);
return MyCompare(b1.OutIndex, b2.OutIndex);
}
@@ -92,39 +103,52 @@ static int CompareFolders(const CFolder &f1, const CFolder &f2)
{
int s1 = f1.Coders.Size();
int s2 = f2.Coders.Size();
- RINOZ(MyCompare(s1, s2));
+ RINOZ_COMP(s1, s2);
int i;
for (i = 0; i < s1; i++)
RINOZ(CompareCoders(f1.Coders[i], f2.Coders[i]));
s1 = f1.BindPairs.Size();
s2 = f2.BindPairs.Size();
- RINOZ(MyCompare(s1, s2));
+ RINOZ_COMP(s1, s2);
for (i = 0; i < s1; i++)
RINOZ(CompareBindPairs(f1.BindPairs[i], f2.BindPairs[i]));
return 0;
}
+/*
static int CompareFiles(const CFileItem &f1, const CFileItem &f2)
{
return MyStringCompareNoCase(f1.Name, f2.Name);
}
+*/
+
+const struct CFolderRepack
+{
+ int FolderIndex;
+ int Group;
+ CNum NumCopyFiles;
+};
-static int CompareFolderRefs(const int *p1, const int *p2, void *param)
+static int CompareFolderRepacks(const CFolderRepack *p1, const CFolderRepack *p2, void *param)
{
- int i1 = *p1;
- int i2 = *p2;
+ RINOZ_COMP(p1->Group, p2->Group);
+ int i1 = p1->FolderIndex;
+ int i2 = p2->FolderIndex;
const CArchiveDatabaseEx &db = *(const CArchiveDatabaseEx *)param;
RINOZ(CompareFolders(
db.Folders[i1],
db.Folders[i2]));
- RINOZ(MyCompare(
+ return MyCompare(i1, i2);
+ /*
+ RINOZ_COMP(
db.NumUnpackStreamsVector[i1],
- db.NumUnpackStreamsVector[i2]));
+ db.NumUnpackStreamsVector[i2]);
if (db.NumUnpackStreamsVector[i1] == 0)
return 0;
return CompareFiles(
db.Files[db.FolderStartFileIndex[i1]],
db.Files[db.FolderStartFileIndex[i2]]);
+ */
}
////////////////////////////////////////////////////////////
@@ -277,20 +301,19 @@ static int CompareUpdateItems(const CRefItem *p1, const CRefItem *p2, void *para
bool sortByType = *(bool *)param;
if (sortByType)
{
- RINOZ(MyCompare(a1.ExtensionIndex, a2.ExtensionIndex))
+ RINOZ_COMP(a1.ExtensionIndex, a2.ExtensionIndex);
RINOZ(MyStringCompareNoCase(u1.Name + a1.ExtensionPos, u2.Name + a2.ExtensionPos));
RINOZ(MyStringCompareNoCase(u1.Name + a1.NamePos, u2.Name + a2.NamePos));
if (!u1.MTimeDefined && u2.MTimeDefined) return 1;
if (u1.MTimeDefined && !u2.MTimeDefined) return -1;
- if (u1.MTimeDefined && u2.MTimeDefined) RINOZ(MyCompare(u1.MTime, u2.MTime));
- RINOZ(MyCompare(u1.Size, u2.Size))
+ if (u1.MTimeDefined && u2.MTimeDefined) RINOZ_COMP(u1.MTime, u2.MTime);
+ RINOZ_COMP(u1.Size, u2.Size);
}
return MyStringCompareNoCase(u1.Name, u2.Name);
}
struct CSolidGroup
{
- CCompressionMethodMode Method;
CRecordVector<UInt32> Indices;
};
@@ -303,7 +326,7 @@ static wchar_t *g_ExeExts[] =
L"sys"
};
-static bool IsExeFile(const UString &ext)
+static bool IsExeExt(const UString &ext)
{
for (int i = 0; i < sizeof(g_ExeExts) / sizeof(g_ExeExts[0]); i++)
if (ext.CompareNoCase(g_ExeExts[i]) == 0)
@@ -311,31 +334,23 @@ static bool IsExeFile(const UString &ext)
return false;
}
-static const UInt64 k_LZMA = 0x030101;
-static const UInt64 k_BCJ = 0x03030103;
-static const UInt64 k_BCJ2 = 0x0303011B;
-
-static bool GetMethodFull(UInt64 methodID,
- UInt32 numInStreams, CMethodFull &methodResult)
+static void GetMethodFull(UInt64 methodID, UInt32 numInStreams, CMethodFull &methodResult)
{
methodResult.Id = methodID;
methodResult.NumInStreams = numInStreams;
methodResult.NumOutStreams = 1;
- return true;
}
-static bool MakeExeMethod(const CCompressionMethodMode &method,
+static void MakeExeMethod(const CCompressionMethodMode &method,
bool bcj2Filter, CCompressionMethodMode &exeMethod)
{
exeMethod = method;
if (bcj2Filter)
{
CMethodFull methodFull;
- if (!GetMethodFull(k_BCJ2, 4, methodFull))
- return false;
+ GetMethodFull(k_BCJ2, 4, methodFull);
exeMethod.Methods.Insert(0, methodFull);
- if (!GetMethodFull(k_LZMA, 1, methodFull))
- return false;
+ GetMethodFull(k_LZMA, 1, methodFull);
{
CProp prop;
prop.Id = NCoderPropID::kAlgorithm;
@@ -383,8 +398,7 @@ static bool MakeExeMethod(const CCompressionMethodMode &method,
else
{
CMethodFull methodFull;
- if (!GetMethodFull(k_BCJ, 1, methodFull))
- return false;
+ GetMethodFull(k_BCJ, 1, methodFull);
exeMethod.Methods.Insert(0, methodFull);
CBind bind;
bind.OutCoder = 0;
@@ -393,55 +407,6 @@ static bool MakeExeMethod(const CCompressionMethodMode &method,
bind.OutStream = 0;
exeMethod.Binds.Add(bind);
}
- return true;
-}
-
-static void SplitFilesToGroups(
- const CCompressionMethodMode &method,
- bool useFilters, bool maxFilter,
- const CObjectVector<CUpdateItem> &updateItems,
- CObjectVector<CSolidGroup> &groups)
-{
- if (method.Methods.Size() != 1 || method.Binds.Size() != 0)
- useFilters = false;
- groups.Clear();
- groups.Add(CSolidGroup());
- groups.Add(CSolidGroup());
- CSolidGroup &generalGroup = groups[0];
- CSolidGroup &exeGroup = groups[1];
- generalGroup.Method = method;
- int i;
- for (i = 0; i < updateItems.Size(); i++)
- {
- const CUpdateItem &ui = updateItems[i];
- if (!ui.NewData)
- continue;
- if (!ui.HasStream())
- continue;
- if (useFilters)
- {
- const UString name = ui.Name;
- int dotPos = name.ReverseFind(L'.');
- if (dotPos >= 0)
- {
- UString ext = name.Mid(dotPos + 1);
- if (IsExeFile(ext))
- {
- exeGroup.Indices.Add(i);
- continue;
- }
- }
- }
- generalGroup.Indices.Add(i);
- }
- if (exeGroup.Indices.Size() > 0)
- if (!MakeExeMethod(method, maxFilter, exeGroup.Method))
- exeGroup.Method = method;
- for (i = 0; i < groups.Size();)
- if (groups[i].Indices.Size() == 0)
- groups.Delete(i);
- else
- i++;
}
static void FromUpdateItemToFileItem(const CUpdateItem &ui,
@@ -462,7 +427,250 @@ static void FromUpdateItemToFileItem(const CUpdateItem &ui,
file.HasStream = ui.HasStream();
}
-static HRESULT Update2(
+class CFolderOutStream2:
+ public ISequentialOutStream,
+ public CMyUnknownImp
+{
+ COutStreamWithCRC *_crcStreamSpec;
+ CMyComPtr<ISequentialOutStream> _crcStream;
+ const CArchiveDatabaseEx *_db;
+ const CBoolVector *_extractStatuses;
+ CMyComPtr<ISequentialOutStream> _outStream;
+ UInt32 _startIndex;
+ int _currentIndex;
+ bool _fileIsOpen;
+ UInt64 _rem;
+
+ void OpenFile();
+ void CloseFile();
+ HRESULT CloseFileAndSetResult();
+ HRESULT ProcessEmptyFiles();
+public:
+ MY_UNKNOWN_IMP
+
+ CFolderOutStream2()
+ {
+ _crcStreamSpec = new COutStreamWithCRC;
+ _crcStream = _crcStreamSpec;
+ }
+
+ HRESULT Init(const CArchiveDatabaseEx *db, UInt32 startIndex,
+ const CBoolVector *extractStatuses, ISequentialOutStream *outStream);
+ void ReleaseOutStream();
+ HRESULT CheckFinishedState() const { return (_currentIndex == _extractStatuses->Size()) ? S_OK: E_FAIL; }
+
+ STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
+};
+
+HRESULT CFolderOutStream2::Init(const CArchiveDatabaseEx *db, UInt32 startIndex,
+ const CBoolVector *extractStatuses, ISequentialOutStream *outStream)
+{
+ _db = db;
+ _startIndex = startIndex;
+ _extractStatuses = extractStatuses;
+ _outStream = outStream;
+
+ _currentIndex = 0;
+ _fileIsOpen = false;
+ return ProcessEmptyFiles();
+}
+
+void CFolderOutStream2::ReleaseOutStream()
+{
+ _outStream.Release();
+ _crcStreamSpec->ReleaseStream();
+}
+
+void CFolderOutStream2::OpenFile()
+{
+ _crcStreamSpec->SetStream((*_extractStatuses)[_currentIndex] ? _outStream : NULL);
+ _crcStreamSpec->Init(true);
+ _fileIsOpen = true;
+ _rem = _db->Files[_startIndex + _currentIndex].Size;
+}
+
+void CFolderOutStream2::CloseFile()
+{
+ _crcStreamSpec->ReleaseStream();
+ _fileIsOpen = false;
+ _currentIndex++;
+}
+
+HRESULT CFolderOutStream2::CloseFileAndSetResult()
+{
+ const CFileItem &file = _db->Files[_startIndex + _currentIndex];
+ CloseFile();
+ return (file.IsDir || !file.CrcDefined || file.Crc == _crcStreamSpec->GetCRC()) ? S_OK: S_FALSE;
+}
+
+HRESULT CFolderOutStream2::ProcessEmptyFiles()
+{
+ while (_currentIndex < _extractStatuses->Size() && _db->Files[_startIndex + _currentIndex].Size == 0)
+ {
+ OpenFile();
+ RINOK(CloseFileAndSetResult());
+ }
+ return S_OK;
+}
+
+STDMETHODIMP CFolderOutStream2::Write(const void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ while (size != 0)
+ {
+ if (_fileIsOpen)
+ {
+ UInt32 cur = size < _rem ? size : (UInt32)_rem;
+ RINOK(_crcStream->Write(data, cur, &cur));
+ if (cur == 0)
+ break;
+ data = (const Byte *)data + cur;
+ size -= cur;
+ _rem -= cur;
+ if (processedSize != NULL)
+ *processedSize += cur;
+ if (_rem == 0)
+ {
+ RINOK(CloseFileAndSetResult());
+ RINOK(ProcessEmptyFiles());
+ continue;
+ }
+ }
+ else
+ {
+ RINOK(ProcessEmptyFiles());
+ if (_currentIndex == _extractStatuses->Size())
+ {
+ // we don't support partial extracting
+ return E_FAIL;
+ }
+ OpenFile();
+ }
+ }
+ return S_OK;
+}
+
+class CThreadDecoder: public CVirtThread
+{
+public:
+ HRESULT Result;
+ CMyComPtr<IInStream> InStream;
+
+ CFolderOutStream2 *FosSpec;
+ CMyComPtr<ISequentialOutStream> Fos;
+
+ UInt64 StartPos;
+ const UInt64 *PackSizes;
+ const CFolder *Folder;
+ #ifndef _NO_CRYPTO
+ CMyComPtr<ICryptoGetTextPassword> GetTextPassword;
+ #endif
+
+ DECL_EXTERNAL_CODECS_VARS
+ CDecoder Decoder;
+
+ #ifdef COMPRESS_MT
+ bool MtMode;
+ UInt32 NumThreads;
+ #endif
+
+ CThreadDecoder():
+ Decoder(true)
+ {
+ #ifdef COMPRESS_MT
+ MtMode = false;
+ NumThreads = 1;
+ #endif
+ FosSpec = new CFolderOutStream2;
+ Fos = FosSpec;
+ Result = E_FAIL;
+ }
+ virtual void Execute();
+};
+
+void CThreadDecoder::Execute()
+{
+ try
+ {
+ #ifndef _NO_CRYPTO
+ bool passwordIsDefined;
+ #endif
+ Result = Decoder.Decode(
+ EXTERNAL_CODECS_VARS
+ InStream,
+ StartPos,
+ PackSizes,
+ *Folder,
+ Fos,
+ NULL
+ #ifndef _NO_CRYPTO
+ , GetTextPassword, passwordIsDefined
+ #endif
+ #ifdef COMPRESS_MT
+ , MtMode, NumThreads
+ #endif
+ );
+ }
+ catch(...)
+ {
+ Result = E_FAIL;
+ }
+ if (Result == S_OK)
+ Result = FosSpec->CheckFinishedState();
+ FosSpec->ReleaseOutStream();
+}
+
+bool static Is86FilteredFolder(const CFolder &f)
+{
+ for (int i = 0; i < f.Coders.Size(); i++)
+ {
+ CMethodId m = f.Coders[i].MethodID;
+ if (m == k_BCJ || m == k_BCJ2)
+ return true;
+ }
+ return false;
+}
+
+bool static IsEncryptedFolder(const CFolder &f)
+{
+ for (int i = 0; i < f.Coders.Size(); i++)
+ {
+ CMethodId m = f.Coders[i].MethodID;
+ if (m == k_AES)
+ return true;
+ }
+ return false;
+}
+
+#ifndef _NO_CRYPTO
+
+class CCryptoGetTextPassword:
+ public ICryptoGetTextPassword,
+ public CMyUnknownImp
+{
+public:
+ UString Password;
+
+ MY_UNKNOWN_IMP
+ STDMETHOD(CryptoGetTextPassword)(BSTR *password);
+};
+
+STDMETHODIMP CCryptoGetTextPassword::CryptoGetTextPassword(BSTR *password)
+{
+ return StringToBstr(Password, password);
+}
+
+#endif
+
+static const int kNumGroupsMax = 4;
+
+static bool Is86Group(int group) { return (group & 1) != 0; }
+static bool IsEncryptedGroup(int group) { return (group & 2) != 0; }
+static int GetGroupIndex(bool encrypted, int bcjFiltered)
+ { return (encrypted ? 2 : 0) + (bcjFiltered ? 1 : 0); }
+
+HRESULT Update(
DECL_EXTERNAL_CODECS_LOC_VARS
IInStream *inStream,
const CArchiveDatabaseEx *db,
@@ -471,7 +679,11 @@ static HRESULT Update2(
CArchiveDatabase &newDatabase,
ISequentialOutStream *seqOutStream,
IArchiveUpdateCallback *updateCallback,
- const CUpdateOptions &options)
+ const CUpdateOptions &options
+ #ifndef _NO_CRYPTO
+ , ICryptoGetTextPassword *getDecoderPassword
+ #endif
+ )
{
UInt64 numSolidFiles = options.NumSolidFiles;
if (numSolidFiles == 0)
@@ -490,153 +702,305 @@ static HRESULT Update2(
}
CRecordVector<int> fileIndexToUpdateIndexMap;
+ CRecordVector<CFolderRepack> folderRefs;
+ UInt64 complexity = 0;
+ UInt64 inSizeForReduce2 = 0;
+ bool needEncryptedRepack = false;
if (db != 0)
{
fileIndexToUpdateIndexMap.Reserve(db->Files.Size());
- for (int i = 0; i < db->Files.Size(); i++)
+ int i;
+ for (i = 0; i < db->Files.Size(); i++)
fileIndexToUpdateIndexMap.Add(-1);
- }
- int i;
- for(i = 0; i < updateItems.Size(); i++)
- {
- int index = updateItems[i].IndexInArchive;
- if (index != -1)
- fileIndexToUpdateIndexMap[index] = i;
- }
- CRecordVector<int> folderRefs;
- if (db != 0)
- {
- for(i = 0; i < db->Folders.Size(); i++)
+ for (i = 0; i < updateItems.Size(); i++)
+ {
+ int index = updateItems[i].IndexInArchive;
+ if (index != -1)
+ fileIndexToUpdateIndexMap[index] = i;
+ }
+
+ for (i = 0; i < db->Folders.Size(); i++)
{
CNum indexInFolder = 0;
CNum numCopyItems = 0;
CNum numUnpackStreams = db->NumUnpackStreamsVector[i];
- for (CNum fileIndex = db->FolderStartFileIndex[i];
- indexInFolder < numUnpackStreams; fileIndex++)
+ UInt64 repackSize = 0;
+ for (CNum fi = db->FolderStartFileIndex[i]; indexInFolder < numUnpackStreams; fi++)
{
- if (db->Files[fileIndex].HasStream)
+ const CFileItem &file = db->Files[fi];
+ if (file.HasStream)
{
indexInFolder++;
- int updateIndex = fileIndexToUpdateIndexMap[fileIndex];
- if (updateIndex >= 0)
- if (!updateItems[updateIndex].NewData)
- numCopyItems++;
+ int updateIndex = fileIndexToUpdateIndexMap[fi];
+ if (updateIndex >= 0 && !updateItems[updateIndex].NewData)
+ {
+ numCopyItems++;
+ repackSize += file.Size;
+ }
}
}
- if (numCopyItems != numUnpackStreams && numCopyItems != 0)
- return E_NOTIMPL; // It needs repacking !!!
- if (numCopyItems > 0)
- folderRefs.Add(i);
+
+ if (numCopyItems == 0)
+ continue;
+
+ CFolderRepack rep;
+ rep.FolderIndex = i;
+ rep.NumCopyFiles = numCopyItems;
+ const CFolder &f = db->Folders[i];
+ bool isEncrypted = IsEncryptedFolder(f);
+ rep.Group = GetGroupIndex(isEncrypted, Is86FilteredFolder(f));
+ folderRefs.Add(rep);
+ if (numCopyItems == numUnpackStreams)
+ complexity += db->GetFolderFullPackSize(i);
+ else
+ {
+ complexity += repackSize;
+ if (repackSize > inSizeForReduce2)
+ inSizeForReduce2 = repackSize;
+ if (isEncrypted)
+ needEncryptedRepack = true;
+ }
}
- folderRefs.Sort(CompareFolderRefs, (void *)db);
+ folderRefs.Sort(CompareFolderRepacks, (void *)db);
}
- ////////////////////////////
-
- RINOK(archive.Create(seqOutStream, false));
- RINOK(archive.SkeepPrefixArchiveHeader());
- UInt64 complexity = 0;
- for(i = 0; i < folderRefs.Size(); i++)
- complexity += db->GetFolderFullPackSize(folderRefs[i]);
UInt64 inSizeForReduce = 0;
- for(i = 0; i < updateItems.Size(); i++)
+ int i;
+ for (i = 0; i < updateItems.Size(); i++)
{
const CUpdateItem &ui = updateItems[i];
if (ui.NewData)
{
complexity += ui.Size;
- if (numSolidFiles == 1)
- {
- if (ui.Size > inSizeForReduce)
- inSizeForReduce = ui.Size;
- }
- else
+ if (numSolidFiles != 1)
inSizeForReduce += ui.Size;
+ else if (ui.Size > inSizeForReduce)
+ inSizeForReduce = ui.Size;
}
}
- RINOK(updateCallback->SetTotal(complexity));
- complexity = 0;
- RINOK(updateCallback->SetCompleted(&complexity));
+ if (inSizeForReduce2 > inSizeForReduce)
+ inSizeForReduce = inSizeForReduce2;
+
+ const UInt32 kMinReduceSize = (1 << 16);
+ if (inSizeForReduce < kMinReduceSize)
+ inSizeForReduce = kMinReduceSize;
+
+ RINOK(updateCallback->SetTotal(complexity));
CLocalProgress *lps = new CLocalProgress;
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(updateCallback, true);
- /////////////////////////////////////////
- // Write Copy Items
+ CThreadDecoder threadDecoder;
+ if (!folderRefs.IsEmpty())
+ {
+ #ifdef EXTERNAL_CODECS
+ threadDecoder._codecsInfo = codecsInfo;
+ threadDecoder._externalCodecs = *externalCodecs;
+ #endif
+ RINOK(threadDecoder.Create());
+ }
+
+ CObjectVector<CSolidGroup> groups;
+ for (i = 0; i < kNumGroupsMax; i++)
+ groups.Add(CSolidGroup());
- for(i = 0; i < folderRefs.Size(); i++)
{
- int folderIndex = folderRefs[i];
-
- lps->ProgressOffset = complexity;
- UInt64 packSize = db->GetFolderFullPackSize(folderIndex);
- RINOK(WriteRange(inStream, archive.SeqStream,
- db->GetFolderStreamPos(folderIndex, 0), packSize, progress));
- complexity += packSize;
-
- const CFolder &folder = db->Folders[folderIndex];
- CNum startIndex = db->FolderStartPackStreamIndex[folderIndex];
- for (int j = 0; j < folder.PackStreams.Size(); j++)
+ // ---------- Split files to 2 groups ----------
+
+ bool useFilters = options.UseFilters;
+ const CCompressionMethodMode &method = *options.Method;
+ if (method.Methods.Size() != 1 || method.Binds.Size() != 0)
+ useFilters = false;
+ for (i = 0; i < updateItems.Size(); i++)
{
- newDatabase.PackSizes.Add(db->PackSizes[startIndex + j]);
- // newDatabase.PackCRCsDefined.Add(db.PackCRCsDefined[startIndex + j]);
- // newDatabase.PackCRCs.Add(db.PackCRCs[startIndex + j]);
+ const CUpdateItem &ui = updateItems[i];
+ if (!ui.NewData || !ui.HasStream())
+ continue;
+ bool filteredGroup = false;
+ if (useFilters)
+ {
+ int dotPos = ui.Name.ReverseFind(L'.');
+ if (dotPos >= 0)
+ filteredGroup = IsExeExt(ui.Name.Mid(dotPos + 1));
+ }
+ groups[GetGroupIndex(method.PasswordIsDefined, filteredGroup)].Indices.Add(i);
}
- newDatabase.Folders.Add(folder);
+ }
- CNum numUnpackStreams = db->NumUnpackStreamsVector[folderIndex];
- newDatabase.NumUnpackStreamsVector.Add(numUnpackStreams);
+ #ifndef _NO_CRYPTO
- CNum indexInFolder = 0;
- for (CNum fi = db->FolderStartFileIndex[folderIndex];
- indexInFolder < numUnpackStreams; fi++)
+ CCryptoGetTextPassword *getPasswordSpec = NULL;
+ if (needEncryptedRepack)
+ {
+ getPasswordSpec = new CCryptoGetTextPassword;
+ threadDecoder.GetTextPassword = getPasswordSpec;
+
+ if (options.Method->PasswordIsDefined)
+ getPasswordSpec->Password = options.Method->Password;
+ else
{
- CFileItem file;
- CFileItem2 file2;
- db->GetFile(fi, file, file2);
- if (file.HasStream)
- {
- indexInFolder++;
- int updateIndex = fileIndexToUpdateIndexMap[fi];
- if (updateIndex >= 0)
- {
- const CUpdateItem &ui = updateItems[updateIndex];
- if (ui.NewProperties)
- {
- CFileItem uf;
- FromUpdateItemToFileItem(ui, uf, file2);
- uf.Size = file.Size;
- uf.Crc = file.Crc;
- uf.CrcDefined = file.CrcDefined;
- uf.HasStream = file.HasStream;
- file = uf;
- }
- }
- newDatabase.AddFile(file, file2);
- }
+ if (!getDecoderPassword)
+ return E_NOTIMPL;
+ CMyComBSTR password;
+ RINOK(getDecoderPassword->CryptoGetTextPassword(&password));
+ getPasswordSpec->Password = password;
}
}
- folderRefs.ClearAndFree();
- fileIndexToUpdateIndexMap.ClearAndFree();
+ #endif
- /////////////////////////////////////////
- // Compress New Files
+ // ---------- Compress ----------
- CObjectVector<CSolidGroup> groups;
- SplitFilesToGroups(*options.Method, options.UseFilters, options.MaxFilter,
- updateItems, groups);
+ RINOK(archive.Create(seqOutStream, false));
+ RINOK(archive.SkipPrefixArchiveHeader());
- const UInt32 kMinReduceSize = (1 << 16);
- if (inSizeForReduce < kMinReduceSize)
- inSizeForReduce = kMinReduceSize;
+ int folderRefIndex = 0;
+ lps->ProgressOffset = 0;
- for (int groupIndex = 0; groupIndex < groups.Size(); groupIndex++)
+ for (int groupIndex = 0; groupIndex < kNumGroupsMax; groupIndex++)
{
const CSolidGroup &group = groups[groupIndex];
+
+ CCompressionMethodMode method;
+ if (Is86Group(groupIndex))
+ MakeExeMethod(*options.Method, options.MaxFilter, method);
+ else
+ method = *options.Method;
+
+ if (IsEncryptedGroup(groupIndex))
+ {
+ if (!method.PasswordIsDefined)
+ {
+ #ifndef _NO_CRYPTO
+ if (getPasswordSpec)
+ method.Password = getPasswordSpec->Password;
+ #endif
+ method.PasswordIsDefined = true;
+ }
+ }
+ else
+ {
+ method.PasswordIsDefined = false;
+ method.Password.Empty();
+ }
+
+ CEncoder encoder(method);
+
+ for (; folderRefIndex < folderRefs.Size(); folderRefIndex++)
+ {
+ const CFolderRepack &rep = folderRefs[folderRefIndex];
+ if (rep.Group != groupIndex)
+ break;
+ int folderIndex = rep.FolderIndex;
+
+ if (rep.NumCopyFiles == db->NumUnpackStreamsVector[folderIndex])
+ {
+ UInt64 packSize = db->GetFolderFullPackSize(folderIndex);
+ RINOK(WriteRange(inStream, archive.SeqStream,
+ db->GetFolderStreamPos(folderIndex, 0), packSize, progress));
+ lps->ProgressOffset += packSize;
+
+ const CFolder &folder = db->Folders[folderIndex];
+ CNum startIndex = db->FolderStartPackStreamIndex[folderIndex];
+ for (int j = 0; j < folder.PackStreams.Size(); j++)
+ {
+ newDatabase.PackSizes.Add(db->PackSizes[startIndex + j]);
+ // newDatabase.PackCRCsDefined.Add(db.PackCRCsDefined[startIndex + j]);
+ // newDatabase.PackCRCs.Add(db.PackCRCs[startIndex + j]);
+ }
+ newDatabase.Folders.Add(folder);
+ }
+ else
+ {
+ CStreamBinder sb;
+ RINOK(sb.CreateEvents());
+ CMyComPtr<ISequentialOutStream> sbOutStream;
+ CMyComPtr<ISequentialInStream> sbInStream;
+ sb.CreateStreams(&sbInStream, &sbOutStream);
+ CBoolVector extractStatuses;
+
+ CNum numUnpackStreams = db->NumUnpackStreamsVector[folderIndex];
+ CNum indexInFolder = 0;
+
+ for (CNum fi = db->FolderStartFileIndex[folderIndex]; indexInFolder < numUnpackStreams; fi++)
+ {
+ bool needExtract = false;
+ if (db->Files[fi].HasStream)
+ {
+ indexInFolder++;
+ int updateIndex = fileIndexToUpdateIndexMap[fi];
+ if (updateIndex >= 0 && !updateItems[updateIndex].NewData)
+ needExtract = true;
+ }
+ extractStatuses.Add(needExtract);
+ }
+
+ RINOK(threadDecoder.FosSpec->Init(db, db->FolderStartFileIndex[folderIndex], &extractStatuses, sbOutStream));
+ sbOutStream.Release();
+
+ threadDecoder.InStream = inStream;
+ threadDecoder.Folder = &db->Folders[folderIndex];
+ threadDecoder.StartPos = db->GetFolderStreamPos(folderIndex, 0);
+ threadDecoder.PackSizes = &db->PackSizes[db->FolderStartPackStreamIndex[folderIndex]];
+
+ threadDecoder.Start();
+
+ int startPackIndex = newDatabase.PackSizes.Size();
+ CFolder newFolder;
+ RINOK(encoder.Encode(
+ EXTERNAL_CODECS_LOC_VARS
+ sbInStream, NULL, &inSizeForReduce, newFolder,
+ archive.SeqStream, newDatabase.PackSizes, progress));
+
+ threadDecoder.WaitFinish();
+
+ RINOK(threadDecoder.Result);
+
+ for (; startPackIndex < newDatabase.PackSizes.Size(); startPackIndex++)
+ lps->OutSize += newDatabase.PackSizes[startPackIndex];
+ lps->InSize += newFolder.GetUnpackSize();
+
+ newDatabase.Folders.Add(newFolder);
+ }
+
+ newDatabase.NumUnpackStreamsVector.Add(rep.NumCopyFiles);
+
+ CNum numUnpackStreams = db->NumUnpackStreamsVector[folderIndex];
+
+ CNum indexInFolder = 0;
+ for (CNum fi = db->FolderStartFileIndex[folderIndex]; indexInFolder < numUnpackStreams; fi++)
+ {
+ CFileItem file;
+ CFileItem2 file2;
+ db->GetFile(fi, file, file2);
+ if (file.HasStream)
+ {
+ indexInFolder++;
+ int updateIndex = fileIndexToUpdateIndexMap[fi];
+ if (updateIndex >= 0)
+ {
+ const CUpdateItem &ui = updateItems[updateIndex];
+ if (ui.NewData)
+ continue;
+ if (ui.NewProps)
+ {
+ CFileItem uf;
+ FromUpdateItemToFileItem(ui, uf, file2);
+ uf.Size = file.Size;
+ uf.Crc = file.Crc;
+ uf.CrcDefined = file.CrcDefined;
+ uf.HasStream = file.HasStream;
+ file = uf;
+ }
+ newDatabase.AddFile(file, file2);
+ }
+ }
+ }
+ }
+
int numFiles = group.Indices.Size();
if (numFiles == 0)
continue;
@@ -657,7 +1021,7 @@ static HRESULT Update2(
/*
const CUpdateItem &ui = updateItems[index];
CFileItem file;
- if (ui.NewProperties)
+ if (ui.NewProps)
FromUpdateItemToFileItem(ui, file);
else
file = db.Files[ui.IndexInArchive];
@@ -667,8 +1031,6 @@ static HRESULT Update2(
*/
}
- CEncoder encoder(group.Method);
-
for (i = 0; i < numFiles;)
{
UInt64 totalSize = 0;
@@ -710,7 +1072,7 @@ static HRESULT Update2(
lps->OutSize += newDatabase.PackSizes[startPackIndex];
lps->InSize += folderItem.GetUnpackSize();
- // for()
+ // for ()
// newDatabase.PackCRCsDefined.Add(false);
// newDatabase.PackCRCs.Add(0);
@@ -722,7 +1084,7 @@ static HRESULT Update2(
const CUpdateItem &ui = updateItems[indices[i + subIndex]];
CFileItem file;
CFileItem2 file2;
- if (ui.NewProperties)
+ if (ui.NewProps)
FromUpdateItemToFileItem(ui, file, file2);
else
db->GetFile(ui.IndexInArchive, file, file2);
@@ -761,14 +1123,20 @@ static HRESULT Update2(
}
}
+ if (folderRefIndex != folderRefs.Size())
+ return E_FAIL;
+
+ /*
+ folderRefs.ClearAndFree();
+ fileIndexToUpdateIndexMap.ClearAndFree();
groups.ClearAndFree();
+ */
{
- /////////////////////////////////////////
- // Write Empty Files & Folders
+ // ---------- Write Folders & Empty Files ----------
CRecordVector<int> emptyRefs;
- for(i = 0; i < updateItems.Size(); i++)
+ for (i = 0; i < updateItems.Size(); i++)
{
const CUpdateItem &ui = updateItems[i];
if (ui.NewData)
@@ -776,10 +1144,8 @@ static HRESULT Update2(
if (ui.HasStream())
continue;
}
- else
- if (ui.IndexInArchive != -1)
- if (db->Files[ui.IndexInArchive].HasStream)
- continue;
+ else if (ui.IndexInArchive != -1 && db->Files[ui.IndexInArchive].HasStream)
+ continue;
emptyRefs.Add(i);
}
emptyRefs.Sort(CompareEmptyItems, (void *)&updateItems);
@@ -788,7 +1154,7 @@ static HRESULT Update2(
const CUpdateItem &ui = updateItems[emptyRefs[i]];
CFileItem file;
CFileItem2 file2;
- if (ui.NewProperties)
+ if (ui.NewProps)
FromUpdateItemToFileItem(ui, file, file2);
else
db->GetFile(ui.IndexInArchive, file, file2);
@@ -800,21 +1166,4 @@ static HRESULT Update2(
return S_OK;
}
-HRESULT Update(
- DECL_EXTERNAL_CODECS_LOC_VARS
- IInStream *inStream,
- const CArchiveDatabaseEx *db,
- const CObjectVector<CUpdateItem> &updateItems,
- COutArchive &archive,
- CArchiveDatabase &newDatabase,
- ISequentialOutStream *seqOutStream,
- IArchiveUpdateCallback *updateCallback,
- const CUpdateOptions &options)
-{
- return Update2(
- EXTERNAL_CODECS_LOC_VARS
- inStream, db, updateItems,
- archive, newDatabase, seqOutStream, updateCallback, options);
-}
-
}}
diff --git a/CPP/7zip/Archive/7z/7zUpdate.h b/CPP/7zip/Archive/7z/7zUpdate.h
index bcc7cef7..31e36224 100755
--- a/CPP/7zip/Archive/7z/7zUpdate.h
+++ b/CPP/7zip/Archive/7z/7zUpdate.h
@@ -3,9 +3,9 @@
#ifndef __7Z_UPDATE_H
#define __7Z_UPDATE_H
+#include "7zCompressionMode.h"
#include "7zIn.h"
#include "7zOut.h"
-#include "7zCompressionMode.h"
#include "../IArchive.h"
@@ -27,7 +27,7 @@ struct CUpdateItem
UInt32 Attrib;
bool NewData;
- bool NewProperties;
+ bool NewProps;
bool IsAnti;
bool IsDir;
@@ -78,7 +78,11 @@ HRESULT Update(
CArchiveDatabase &newDatabase,
ISequentialOutStream *seqOutStream,
IArchiveUpdateCallback *updateCallback,
- const CUpdateOptions &options);
+ const CUpdateOptions &options
+ #ifndef _NO_CRYPTO
+ , ICryptoGetTextPassword *getDecoderPassword
+ #endif
+ );
}}
#endif
diff --git a/CPP/7zip/Archive/7z/makefile b/CPP/7zip/Archive/7z/makefile
index 1a72da0e..4489f290 100755
--- a/CPP/7zip/Archive/7z/makefile
+++ b/CPP/7zip/Archive/7z/makefile
@@ -104,7 +104,7 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(AR_COMMON_OBJS): ../Common/$(*B).cpp
$(COMPL)
-$O\CopyCoder.obj: ../../Compress/Copy/$(*B).cpp
+$O\CopyCoder.obj: ../../Compress/$(*B).cpp
$(COMPL)
$(C_OBJS): ../../../../C/$(*B).c
$(COMPL_O2)
diff --git a/CPP/7zip/Archive/ArchiveExports.cpp b/CPP/7zip/Archive/ArchiveExports.cpp
index ae388d67..f7bc9c69 100755
--- a/CPP/7zip/Archive/ArchiveExports.cpp
+++ b/CPP/7zip/Archive/ArchiveExports.cpp
@@ -3,15 +3,12 @@
#include "StdAfx.h"
#include "../../Common/ComTry.h"
-#include "../../Common/Types.h"
+
#include "../../Windows/PropVariant.h"
-#include "../Common/RegisterArc.h"
-#include "IArchive.h"
-#include "../ICoder.h"
-#include "../IPassword.h"
+#include "../Common/RegisterArc.h"
-static const unsigned int kNumArcsMax = 32;
+static const unsigned int kNumArcsMax = 48;
static unsigned int g_NumArcs = 0;
static const CArcInfo *g_Arcs[kNumArcsMax];
void RegisterArc(const CArcInfo *arcInfo)
diff --git a/CPP/7zip/Archive/ArjHandler.cpp b/CPP/7zip/Archive/ArjHandler.cpp
index c40cbbcd..66ad1677 100755
--- a/CPP/7zip/Archive/ArjHandler.cpp
+++ b/CPP/7zip/Archive/ArjHandler.cpp
@@ -2,14 +2,14 @@
#include "StdAfx.h"
+#include "../../../C/CpuArch.h"
+
#include "Common/ComTry.h"
#include "Common/StringConvert.h"
#include "Windows/PropVariant.h"
#include "Windows/Time.h"
-#include "../../../C/CpuArch.h"
-
#include "../Common/LimitedStreams.h"
#include "../Common/ProgressUtils.h"
#include "../Common/RegisterArc.h"
@@ -180,6 +180,7 @@ struct CItem
UInt32 PackSize;
UInt32 Size;
UInt32 FileCRC;
+ UInt32 SplitPos;
Byte Version;
Byte ExtractVersion;
@@ -197,6 +198,8 @@ struct CItem
bool IsEncrypted() const { return (Flags & NFileHeader::NFlags::kGarbled) != 0; }
bool IsDir() const { return (FileType == NFileHeader::NFileType::kDirectory); }
+ bool IsSplitAfter() const { return (Flags & NFileHeader::NFlags::kVolume) != 0; }
+ bool IsSplitBefore() const { return (Flags & NFileHeader::NFlags::kExtFile) != 0; }
UInt32 GetWinAttributes() const
{
UInt32 winAtrributes;
@@ -240,6 +243,10 @@ HRESULT CItem::Parse(const Byte *p, unsigned size)
// FirstChapter = p[28];
// FirstChapter = p[29];
+ SplitPos = 0;
+ if (IsSplitBefore() && firstHeaderSize >= 34)
+ SplitPos = Get32(p + 30);
+
unsigned pos = firstHeaderSize;
unsigned size1 = size - pos;
RINOK(ReadString(p + pos, size1, Name));
@@ -270,7 +277,7 @@ class CInArchive
HRESULT ReadBlock(bool &filled);
HRESULT ReadSignatureAndBlock(bool &filled);
- HRESULT SkeepExtendedHeaders();
+ HRESULT SkipExtendedHeaders();
HRESULT SafeReadBytes(void *data, UInt32 size);
@@ -389,7 +396,7 @@ HRESULT CInArchive::ReadSignatureAndBlock(bool &filled)
return ReadBlock(filled);
}
-HRESULT CInArchive::SkeepExtendedHeaders()
+HRESULT CInArchive::SkipExtendedHeaders()
{
for (UInt32 i = 0;; i++)
{
@@ -412,7 +419,7 @@ HRESULT CInArchive::Open(const UInt64 *searchHeaderSizeLimit)
if (!filled)
return S_FALSE;
RINOK(Header.Parse(_block, _blockSize));
- return SkeepExtendedHeaders();
+ return SkipExtendedHeaders();
}
HRESULT CInArchive::GetNextItem(bool &filled, CItem &item)
@@ -428,7 +435,7 @@ HRESULT CInArchive::GetNextItem(bool &filled, CItem &item)
extraData = GetUi32(_block + pos);
*/
- RINOK(SkeepExtendedHeaders());
+ RINOK(SkipExtendedHeaders());
filled = true;
return S_OK;
}
@@ -482,8 +489,9 @@ STATPROPSTG kProps[] =
{
{ NULL, kpidPath, VT_BSTR},
{ NULL, kpidIsDir, VT_BOOL},
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidSize, VT_UI4},
+ { NULL, kpidPosition, VT_UI8},
+ { NULL, kpidPackSize, VT_UI4},
{ NULL, kpidMTime, VT_FILETIME},
{ NULL, kpidAttrib, VT_UI4},
{ NULL, kpidEncrypted, VT_BOOL},
@@ -556,6 +564,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidIsDir: prop = item.IsDir(); break;
case kpidSize: prop = item.Size; break;
case kpidPackSize: prop = item.PackSize; break;
+ case kpidPosition: if (item.IsSplitBefore() || item.IsSplitAfter()) prop = (UInt64)item.SplitPos; break;
case kpidAttrib: prop = item.GetWinAttributes(); break;
case kpidEncrypted: prop = item.IsEncrypted(); break;
case kpidCRC: prop = item.FileCRC; break;
diff --git a/CPP/7zip/Archive/BZip2/BZip2Handler.cpp b/CPP/7zip/Archive/BZip2/BZip2Handler.cpp
deleted file mode 100755
index 05716b62..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2Handler.cpp
+++ /dev/null
@@ -1,216 +0,0 @@
-// BZip2Handler.cpp
-
-#include "StdAfx.h"
-
-#include "Common/ComTry.h"
-
-#include "Windows/PropVariant.h"
-
-#include "../../Common/CreateCoder.h"
-#include "../../Common/ProgressUtils.h"
-#include "../../Common/StreamUtils.h"
-
-#include "../Common/DummyOutStream.h"
-
-#include "BZip2Handler.h"
-
-using namespace NWindows;
-
-namespace NArchive {
-namespace NBZip2 {
-
-static const CMethodId kMethodId_BZip2 = 0x040202;
-
-STATPROPSTG kProps[] =
-{
- { NULL, kpidPackSize, VT_UI8}
-};
-
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
-
-STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
-{
- *numItems = 1;
- return S_OK;
-}
-
-STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
-{
- NWindows::NCOM::CPropVariant prop;
- switch(propID)
- {
- case kpidPackSize: prop = _item.PackSize; break;
- }
- prop.Detach(value);
- return S_OK;
-}
-
-STDMETHODIMP CHandler::Open(IInStream *stream,
- const UInt64 * /* maxCheckStartPosition */,
- IArchiveOpenCallback * /* openArchiveCallback */)
-{
- COM_TRY_BEGIN
- try
- {
- RINOK(stream->Seek(0, STREAM_SEEK_CUR, &_streamStartPosition));
- const int kSignatureSize = 3;
- Byte buffer[kSignatureSize];
- RINOK(ReadStream_FALSE(stream, buffer, kSignatureSize));
- if (buffer[0] != 'B' || buffer[1] != 'Z' || buffer[2] != 'h')
- return S_FALSE;
-
- UInt64 endPosition;
- RINOK(stream->Seek(0, STREAM_SEEK_END, &endPosition));
- _item.PackSize = endPosition - _streamStartPosition;
-
- _stream = stream;
- }
- catch(...)
- {
- return S_FALSE;
- }
- return S_OK;
- COM_TRY_END
-}
-
-STDMETHODIMP CHandler::Close()
-{
- _stream.Release();
- return S_OK;
-}
-
-
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 testModeSpec, IArchiveExtractCallback *extractCallback)
-{
- COM_TRY_BEGIN
- bool allFilesMode = (numItems == UInt32(-1));
- if (!allFilesMode)
- {
- if (numItems == 0)
- return S_OK;
- if (numItems != 1)
- return E_INVALIDARG;
- if (indices[0] != 0)
- return E_INVALIDARG;
- }
-
- bool testMode = (testModeSpec != 0);
-
- extractCallback->SetTotal(_item.PackSize);
-
- UInt64 currentTotalPacked = 0;
-
- RINOK(extractCallback->SetCompleted(&currentTotalPacked));
-
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode;
- askMode = testMode ? NExtract::NAskMode::kTest :
- NExtract::NAskMode::kExtract;
-
- RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
-
- if(!testMode && !realOutStream)
- return S_OK;
-
-
- extractCallback->PrepareOperation(askMode);
-
- CMyComPtr<ICompressCoder> decoder;
- HRESULT loadResult = CreateCoder(
- EXTERNAL_CODECS_VARS
- kMethodId_BZip2, decoder, false);
- if (loadResult != S_OK || !decoder)
- {
- RINOK(extractCallback->SetOperationResult(NExtract::NOperationResult::kUnSupportedMethod));
- return S_OK;
- }
-
- #ifdef COMPRESS_MT
- {
- CMyComPtr<ICompressSetCoderMt> setCoderMt;
- decoder.QueryInterface(IID_ICompressSetCoderMt, &setCoderMt);
- if (setCoderMt)
- {
- RINOK(setCoderMt->SetNumberOfThreads(_numThreads));
- }
- }
- #endif
-
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
-
- realOutStream.Release();
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(extractCallback, true);
-
- RINOK(_stream->Seek(_streamStartPosition, STREAM_SEEK_SET, NULL));
-
- HRESULT result = S_OK;
-
- bool firstItem = true;
- for (;;)
- {
- lps->InSize = currentTotalPacked;
- lps->OutSize = outStreamSpec->GetSize();
-
- RINOK(lps->SetCur());
-
- const int kSignatureSize = 3;
- Byte buffer[kSignatureSize];
- size_t processedSize = kSignatureSize;
- RINOK(ReadStream(_stream, buffer, &processedSize));
- if (processedSize != kSignatureSize)
- {
- if (firstItem)
- return E_FAIL;
- break;
- }
- if (buffer[0] != 'B' || buffer[1] != 'Z' || buffer[2] != 'h')
- {
- if (firstItem)
- return E_FAIL;
- break;
- }
- firstItem = false;
-
- UInt64 dataStartPos;
- RINOK(_stream->Seek((UInt64)(Int64)(-3), STREAM_SEEK_CUR, &dataStartPos));
-
- result = decoder->Code(_stream, outStream, NULL, NULL, progress);
-
- if (result != S_OK)
- break;
-
- CMyComPtr<ICompressGetInStreamProcessedSize> getInStreamProcessedSize;
- decoder.QueryInterface(IID_ICompressGetInStreamProcessedSize, &getInStreamProcessedSize);
- if (!getInStreamProcessedSize)
- break;
- UInt64 packSize;
- RINOK(getInStreamProcessedSize->GetInStreamProcessedSize(&packSize));
- UInt64 pos;
- RINOK(_stream->Seek(dataStartPos + packSize, STREAM_SEEK_SET, &pos));
- currentTotalPacked = pos - _streamStartPosition;
- }
- outStream.Release();
-
- Int32 retResult;
- if (result == S_OK)
- retResult = NExtract::NOperationResult::kOK;
- else if (result == S_FALSE)
- retResult = NExtract::NOperationResult::kDataError;
- else
- return result;
- return extractCallback->SetOperationResult(retResult);
-
- COM_TRY_END
-}
-
-IMPL_ISetCompressCodecsInfo
-
-}}
diff --git a/CPP/7zip/Archive/BZip2/BZip2Handler.h b/CPP/7zip/Archive/BZip2/BZip2Handler.h
deleted file mode 100755
index 5bb3360a..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2Handler.h
+++ /dev/null
@@ -1,68 +0,0 @@
-// BZip2/Handler.h
-
-#ifndef __BZIP2_HANDLER_H
-#define __BZIP2_HANDLER_H
-
-#include "Common/MyCom.h"
-#include "../IArchive.h"
-#include "../../Common/CreateCoder.h"
-#include "BZip2Item.h"
-
-#ifdef COMPRESS_MT
-#include "../../../Windows/System.h"
-#endif
-
-namespace NArchive {
-namespace NBZip2 {
-
-class CHandler:
- public IInArchive,
- public IOutArchive,
- public ISetProperties,
- PUBLIC_ISetCompressCodecsInfo
- public CMyUnknownImp
-{
- CMyComPtr<IInStream> _stream;
- NArchive::NBZip2::CItem _item;
- UInt64 _streamStartPosition;
-
- UInt32 _level;
- UInt32 _dicSize;
- UInt32 _numPasses;
- #ifdef COMPRESS_MT
- UInt32 _numThreads;
- #endif
-
- DECL_EXTERNAL_CODECS_VARS
-
- void InitMethodProperties()
- {
- _level = 5;
- _dicSize =
- _numPasses = 0xFFFFFFFF;
- #ifdef COMPRESS_MT
- _numThreads = NWindows::NSystem::GetNumberOfProcessors();;
- #endif
- }
-
-public:
- MY_QUERYINTERFACE_BEGIN2(IInArchive)
- MY_QUERYINTERFACE_ENTRY(IOutArchive)
- MY_QUERYINTERFACE_ENTRY(ISetProperties)
- QUERY_ENTRY_ISetCompressCodecsInfo
- MY_QUERYINTERFACE_END
- MY_ADDREF_RELEASE
-
- INTERFACE_IInArchive(;)
- INTERFACE_IOutArchive(;)
-
- STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties);
-
- DECL_ISetCompressCodecsInfo
-
- CHandler() { InitMethodProperties(); }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/BZip2/BZip2HandlerOut.cpp b/CPP/7zip/Archive/BZip2/BZip2HandlerOut.cpp
deleted file mode 100755
index 71311c32..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2HandlerOut.cpp
+++ /dev/null
@@ -1,156 +0,0 @@
-// BZip2HandlerOut.cpp
-
-#include "StdAfx.h"
-
-#include "BZip2Handler.h"
-#include "BZip2Update.h"
-
-#include "Common/Defs.h"
-
-#include "Windows/PropVariant.h"
-
-#include "../../Compress/CopyCoder.h"
-
-#include "../Common/ParseProperties.h"
-
-using namespace NWindows;
-
-static const UInt32 kNumPassesX1 = 1;
-static const UInt32 kNumPassesX7 = 2;
-static const UInt32 kNumPassesX9 = 7;
-
-static const UInt32 kDicSizeX1 = 100000;
-static const UInt32 kDicSizeX3 = 500000;
-static const UInt32 kDicSizeX5 = 900000;
-
-namespace NArchive {
-namespace NBZip2 {
-
-STDMETHODIMP CHandler::GetFileTimeType(UInt32 *type)
-{
- *type = NFileTimeType::kUnix;
- return S_OK;
-}
-
-static HRESULT CopyStreams(ISequentialInStream *inStream, ISequentialOutStream *outStream)
-{
- CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
- return copyCoder->Code(inStream, outStream, NULL, NULL, NULL);
-}
-
-STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
- IArchiveUpdateCallback *updateCallback)
-{
- if (numItems != 1)
- return E_INVALIDARG;
-
- Int32 newData;
- Int32 newProperties;
- UInt32 indexInArchive;
- if (!updateCallback)
- return E_FAIL;
- RINOK(updateCallback->GetUpdateItemInfo(0,&newData, &newProperties, &indexInArchive));
-
- if (IntToBool(newProperties))
- {
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(0, kpidIsDir, &prop));
- if (prop.vt == VT_BOOL)
- {
- if (prop.boolVal != VARIANT_FALSE)
- return E_INVALIDARG;
- }
- else if (prop.vt != VT_EMPTY)
- return E_INVALIDARG;
- }
- }
-
- if (IntToBool(newData))
- {
- UInt64 size;
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(0, kpidSize, &prop));
- if (prop.vt != VT_UI8)
- return E_INVALIDARG;
- size = prop.uhVal.QuadPart;
- }
-
- UInt32 dicSize = _dicSize;
- if (dicSize == 0xFFFFFFFF)
- dicSize = (_level >= 5 ? kDicSizeX5 :
- (_level >= 3 ? kDicSizeX3 :
- kDicSizeX1));
-
- UInt32 numPasses = _numPasses;
- if (numPasses == 0xFFFFFFFF)
- numPasses = (_level >= 9 ? kNumPassesX9 :
- (_level >= 7 ? kNumPassesX7 :
- kNumPassesX1));
-
- return UpdateArchive(
- EXTERNAL_CODECS_VARS
- size, outStream, 0, dicSize, numPasses,
- #ifdef COMPRESS_MT
- _numThreads,
- #endif
- updateCallback);
- }
- if (indexInArchive != 0)
- return E_INVALIDARG;
- RINOK(_stream->Seek(_streamStartPosition, STREAM_SEEK_SET, NULL));
- return CopyStreams(_stream, outStream);
-}
-
-STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties)
-{
- InitMethodProperties();
- #ifdef COMPRESS_MT
- const UInt32 numProcessors = NSystem::GetNumberOfProcessors();
- _numThreads = numProcessors;
- #endif
-
- for (int i = 0; i < numProperties; i++)
- {
- UString name = UString(names[i]);
- name.MakeUpper();
- if (name.IsEmpty())
- return E_INVALIDARG;
-
- const PROPVARIANT &prop = values[i];
-
- if (name[0] == 'X')
- {
- UInt32 level = 9;
- RINOK(ParsePropValue(name.Mid(1), prop, level));
- _level = level;
- continue;
- }
- if (name[0] == 'D')
- {
- UInt32 dicSize = kDicSizeX5;
- RINOK(ParsePropDictionaryValue(name.Mid(1), prop, dicSize));
- _dicSize = dicSize;
- continue;
- }
- if (name.Left(4) == L"PASS")
- {
- UInt32 num = kNumPassesX9;
- RINOK(ParsePropValue(name.Mid(4), prop, num));
- _numPasses = num;
- continue;
- }
- if (name.Left(2) == L"MT")
- {
- #ifdef COMPRESS_MT
- RINOK(ParseMtProp(name.Mid(2), prop, numProcessors, _numThreads));
- #endif
- continue;
- }
- return E_INVALIDARG;
- }
- return S_OK;
-}
-
-}}
diff --git a/CPP/7zip/Archive/BZip2/BZip2Item.h b/CPP/7zip/Archive/BZip2/BZip2Item.h
deleted file mode 100755
index d7508ab9..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2Item.h
+++ /dev/null
@@ -1,20 +0,0 @@
-// Archive/BZip2Item.h
-
-#ifndef __ARCHIVE_BZIP2_ITEM_H
-#define __ARCHIVE_BZIP2_ITEM_H
-
-namespace NArchive {
-namespace NBZip2 {
-
-struct CItem
-{
- UInt64 PackSize;
- UInt64 UnPackSize;
-};
-
-}}
-
-#endif
-
-
-
diff --git a/CPP/7zip/Archive/BZip2/BZip2Update.cpp b/CPP/7zip/Archive/BZip2/BZip2Update.cpp
deleted file mode 100755
index 300d8844..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2Update.cpp
+++ /dev/null
@@ -1,74 +0,0 @@
-// BZip2Update.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/ProgressUtils.h"
-#include "../../Common/CreateCoder.h"
-#include "Windows/PropVariant.h"
-
-#include "BZip2Update.h"
-
-namespace NArchive {
-namespace NBZip2 {
-
-static const CMethodId kMethodId_BZip2 = 0x040202;
-
-HRESULT UpdateArchive(
- DECL_EXTERNAL_CODECS_LOC_VARS
- UInt64 unpackSize,
- ISequentialOutStream *outStream,
- int indexInClient,
- UInt32 dictionary,
- UInt32 numPasses,
- #ifdef COMPRESS_MT
- UInt32 numThreads,
- #endif
- IArchiveUpdateCallback *updateCallback)
-{
- RINOK(updateCallback->SetTotal(unpackSize));
- UInt64 complexity = 0;
- RINOK(updateCallback->SetCompleted(&complexity));
-
- CMyComPtr<ISequentialInStream> fileInStream;
-
- RINOK(updateCallback->GetStream(indexInClient, &fileInStream));
-
- CLocalProgress *localProgressSpec = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> localProgress = localProgressSpec;
- localProgressSpec->Init(updateCallback, true);
-
- CMyComPtr<ICompressCoder> encoder;
- RINOK(CreateCoder(
- EXTERNAL_CODECS_LOC_VARS
- kMethodId_BZip2, encoder, true));
- if (!encoder)
- return E_NOTIMPL;
- CMyComPtr<ICompressSetCoderProperties> setCoderProperties;
- encoder.QueryInterface(IID_ICompressSetCoderProperties, &setCoderProperties);
- if (setCoderProperties)
- {
- NWindows::NCOM::CPropVariant properties[] =
- {
- dictionary,
- numPasses
- #ifdef COMPRESS_MT
- , numThreads
- #endif
- };
- PROPID propIDs[] =
- {
- NCoderPropID::kDictionarySize,
- NCoderPropID::kNumPasses
- #ifdef COMPRESS_MT
- , NCoderPropID::kNumThreads
- #endif
- };
- RINOK(setCoderProperties->SetCoderProperties(propIDs, properties, sizeof(propIDs) / sizeof(propIDs[0])));
- }
-
- RINOK(encoder->Code(fileInStream, outStream, NULL, NULL, localProgress));
-
- return updateCallback->SetOperationResult(NArchive::NUpdate::NOperationResult::kOK);
-}
-
-}}
diff --git a/CPP/7zip/Archive/BZip2/BZip2Update.h b/CPP/7zip/Archive/BZip2/BZip2Update.h
deleted file mode 100755
index e54a7e16..00000000
--- a/CPP/7zip/Archive/BZip2/BZip2Update.h
+++ /dev/null
@@ -1,26 +0,0 @@
-// BZip2Update.h
-
-#ifndef __BZIP2_UPDATE_H
-#define __BZIP2_UPDATE_H
-
-#include "../IArchive.h"
-#include "../../Common/CreateCoder.h"
-
-namespace NArchive {
-namespace NBZip2 {
-
-HRESULT UpdateArchive(
- DECL_EXTERNAL_CODECS_LOC_VARS
- UInt64 unpackSize,
- ISequentialOutStream *outStream,
- int indexInClient,
- UInt32 dictionary,
- UInt32 numPasses,
- #ifdef COMPRESS_MT
- UInt32 numThreads,
- #endif
- IArchiveUpdateCallback *updateCallback);
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/BZip2/StdAfx.h b/CPP/7zip/Archive/BZip2/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/BZip2/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/BZip2/bz2Register.cpp b/CPP/7zip/Archive/BZip2/bz2Register.cpp
deleted file mode 100755
index 76d3d25b..00000000
--- a/CPP/7zip/Archive/BZip2/bz2Register.cpp
+++ /dev/null
@@ -1,18 +0,0 @@
-// BZip2Register.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "BZip2Handler.h"
-static IInArchive *CreateArc() { return new NArchive::NBZip2::CHandler; }
-#ifndef EXTRACT_ONLY
-static IOutArchive *CreateArcOut() { return new NArchive::NBZip2::CHandler; }
-#else
-#define CreateArcOut 0
-#endif
-
-static CArcInfo g_ArcInfo =
- { L"BZip2", L"bz2 bzip2 tbz2 tbz", L"* * .tar .tar", 2, { 'B', 'Z', 'h' }, 3, true, CreateArc, CreateArcOut };
-
-REGISTER_ARC(BZip2)
diff --git a/CPP/7zip/Archive/Bz2Handler.cpp b/CPP/7zip/Archive/Bz2Handler.cpp
new file mode 100755
index 00000000..9b2c4048
--- /dev/null
+++ b/CPP/7zip/Archive/Bz2Handler.cpp
@@ -0,0 +1,428 @@
+// Bz2Handler.cpp
+
+#include "StdAfx.h"
+
+#include "Common/ComTry.h"
+
+#include "Windows/PropVariant.h"
+
+#ifdef COMPRESS_MT
+#include "../../Windows/System.h"
+#endif
+
+#include "../Common/CreateCoder.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/BZip2Decoder.h"
+#include "../Compress/BZip2Encoder.h"
+#include "../Compress/CopyCoder.h"
+
+#include "Common/DummyOutStream.h"
+#include "Common/ParseProperties.h"
+
+using namespace NWindows;
+
+namespace NArchive {
+namespace NBz2 {
+
+static const UInt32 kNumPassesX1 = 1;
+static const UInt32 kNumPassesX7 = 2;
+static const UInt32 kNumPassesX9 = 7;
+
+static const UInt32 kDicSizeX1 = 100000;
+static const UInt32 kDicSizeX3 = 500000;
+static const UInt32 kDicSizeX5 = 900000;
+
+class CHandler:
+ public IInArchive,
+ public IArchiveOpenSeq,
+ public IOutArchive,
+ public ISetProperties,
+ public CMyUnknownImp
+{
+ CMyComPtr<IInStream> _stream;
+ CMyComPtr<ISequentialInStream> _seqStream;
+ UInt64 _packSize;
+ UInt64 _startPosition;
+ bool _packSizeDefined;
+
+ UInt32 _level;
+ UInt32 _dicSize;
+ UInt32 _numPasses;
+ #ifdef COMPRESS_MT
+ UInt32 _numThreads;
+ #endif
+
+ void InitMethodProperties()
+ {
+ _level = 5;
+ _dicSize =
+ _numPasses = 0xFFFFFFFF;
+ #ifdef COMPRESS_MT
+ _numThreads = NWindows::NSystem::GetNumberOfProcessors();;
+ #endif
+ }
+
+public:
+ MY_UNKNOWN_IMP4(IInArchive, IArchiveOpenSeq, IOutArchive, ISetProperties)
+
+ INTERFACE_IInArchive(;)
+ INTERFACE_IOutArchive(;)
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream);
+ STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProps);
+
+ CHandler() { InitMethodProperties(); }
+};
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPackSize, VT_UI8}
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPhySize: if (_packSizeDefined) prop = _packSize; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = 1;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
+{
+ NWindows::NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPackSize: if (_packSizeDefined) prop = _packSize; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream,
+ const UInt64 * /* maxCheckStartPosition */,
+ IArchiveOpenCallback * /* openArchiveCallback */)
+{
+ COM_TRY_BEGIN
+ try
+ {
+ Close();
+ RINOK(stream->Seek(0, STREAM_SEEK_CUR, &_startPosition));
+ const int kSignatureSize = 3;
+ Byte buf[kSignatureSize];
+ RINOK(ReadStream_FALSE(stream, buf, kSignatureSize));
+ if (buf[0] != 'B' || buf[1] != 'Z' || buf[2] != 'h')
+ return S_FALSE;
+
+ UInt64 endPosition;
+ RINOK(stream->Seek(0, STREAM_SEEK_END, &endPosition));
+ _packSize = endPosition - _startPosition;
+ _packSizeDefined = true;
+ _stream = stream;
+ _seqStream = stream;
+ }
+ catch(...) { return S_FALSE; }
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::OpenSeq(ISequentialInStream *stream)
+{
+ Close();
+ _seqStream = stream;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _packSizeDefined = false;
+ _seqStream.Release();
+ _stream.Release();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool allFilesMode = (numItems == (UInt32)-1);
+ if (!allFilesMode)
+ {
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
+ }
+
+ bool testMode = (_aTestMode != 0);
+ if (_stream)
+ extractCallback->SetTotal(_packSize);
+ UInt64 currentTotalPacked = 0;
+ RINOK(extractCallback->SetCompleted(&currentTotalPacked));
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
+ if (!testMode && !realOutStream)
+ return S_OK;
+
+ extractCallback->PrepareOperation(askMode);
+
+ NCompress::NBZip2::CDecoder *decoderSpec = new NCompress::NBZip2::CDecoder;
+ CMyComPtr<ICompressCoder> decoder = decoderSpec;
+
+ if (_stream)
+ {
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ }
+
+ decoderSpec->SetInStream(_seqStream);
+
+ #if defined( COMPRESS_MT) && defined( COMPRESS_BZIP2_MT)
+ RINOK(decoderSpec->SetNumberOfThreads(_numThreads));
+ #endif
+
+ CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+ outStreamSpec->SetStream(realOutStream);
+ outStreamSpec->Init();
+
+ realOutStream.Release();
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, true);
+
+ HRESULT result = S_OK;
+
+ bool firstItem = true;
+ for (;;)
+ {
+ lps->InSize = currentTotalPacked;
+ lps->OutSize = outStreamSpec->GetSize();
+
+ RINOK(lps->SetCur());
+
+ bool isBz2;
+ result = decoderSpec->CodeResume(outStream, isBz2, progress);
+
+ if (result != S_OK)
+ break;
+ if (!isBz2)
+ {
+ if (firstItem)
+ result = S_FALSE;
+ break;
+ }
+ firstItem = false;
+
+ _packSize = currentTotalPacked = decoderSpec->GetInputProcessedSize();
+ _packSizeDefined = true;
+ }
+ decoderSpec->ReleaseInStream();
+ outStream.Release();
+
+ Int32 retResult;
+ if (result == S_OK)
+ retResult = NExtract::NOperationResult::kOK;
+ else if (result == S_FALSE)
+ retResult = NExtract::NOperationResult::kDataError;
+ else
+ return result;
+ return extractCallback->SetOperationResult(retResult);
+
+ COM_TRY_END
+}
+
+static HRESULT UpdateArchive(
+ UInt64 unpackSize,
+ ISequentialOutStream *outStream,
+ int indexInClient,
+ UInt32 dictionary,
+ UInt32 numPasses,
+ #ifdef COMPRESS_MT
+ UInt32 numThreads,
+ #endif
+ IArchiveUpdateCallback *updateCallback)
+{
+ RINOK(updateCallback->SetTotal(unpackSize));
+ UInt64 complexity = 0;
+ RINOK(updateCallback->SetCompleted(&complexity));
+
+ CMyComPtr<ISequentialInStream> fileInStream;
+
+ RINOK(updateCallback->GetStream(indexInClient, &fileInStream));
+
+ CLocalProgress *localProgressSpec = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> localProgress = localProgressSpec;
+ localProgressSpec->Init(updateCallback, true);
+
+ NCompress::NBZip2::CEncoder *encoderSpec = new NCompress::NBZip2::CEncoder;
+ CMyComPtr<ICompressCoder> encoder = encoderSpec;
+ {
+ NWindows::NCOM::CPropVariant properties[] =
+ {
+ dictionary,
+ numPasses
+ #ifdef COMPRESS_MT
+ , numThreads
+ #endif
+ };
+ PROPID propIDs[] =
+ {
+ NCoderPropID::kDictionarySize,
+ NCoderPropID::kNumPasses
+ #ifdef COMPRESS_MT
+ , NCoderPropID::kNumThreads
+ #endif
+ };
+ RINOK(encoderSpec->SetCoderProperties(propIDs, properties, sizeof(propIDs) / sizeof(propIDs[0])));
+ }
+
+ RINOK(encoder->Code(fileInStream, outStream, NULL, NULL, localProgress));
+
+ return updateCallback->SetOperationResult(NArchive::NUpdate::NOperationResult::kOK);
+}
+
+STDMETHODIMP CHandler::GetFileTimeType(UInt32 *type)
+{
+ *type = NFileTimeType::kUnix;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
+ IArchiveUpdateCallback *updateCallback)
+{
+ if (numItems != 1)
+ return E_INVALIDARG;
+
+ Int32 newData, newProps;
+ UInt32 indexInArchive;
+ if (!updateCallback)
+ return E_FAIL;
+ RINOK(updateCallback->GetUpdateItemInfo(0, &newData, &newProps, &indexInArchive));
+
+ if (IntToBool(newProps))
+ {
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidIsDir, &prop));
+ if (prop.vt == VT_BOOL)
+ {
+ if (prop.boolVal != VARIANT_FALSE)
+ return E_INVALIDARG;
+ }
+ else if (prop.vt != VT_EMPTY)
+ return E_INVALIDARG;
+ }
+ }
+
+ if (IntToBool(newData))
+ {
+ UInt64 size;
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidSize, &prop));
+ if (prop.vt != VT_UI8)
+ return E_INVALIDARG;
+ size = prop.uhVal.QuadPart;
+ }
+
+ UInt32 dicSize = _dicSize;
+ if (dicSize == 0xFFFFFFFF)
+ dicSize = (_level >= 5 ? kDicSizeX5 :
+ (_level >= 3 ? kDicSizeX3 :
+ kDicSizeX1));
+
+ UInt32 numPasses = _numPasses;
+ if (numPasses == 0xFFFFFFFF)
+ numPasses = (_level >= 9 ? kNumPassesX9 :
+ (_level >= 7 ? kNumPassesX7 :
+ kNumPassesX1));
+
+ return UpdateArchive(
+ size, outStream, 0, dicSize, numPasses,
+ #ifdef COMPRESS_MT
+ _numThreads,
+ #endif
+ updateCallback);
+ }
+ if (indexInArchive != 0)
+ return E_INVALIDARG;
+ if (_stream)
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ return NCompress::CopyStream(_stream, outStream, NULL);
+}
+
+STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProps)
+{
+ InitMethodProperties();
+ #ifdef COMPRESS_MT
+ const UInt32 numProcessors = NSystem::GetNumberOfProcessors();
+ _numThreads = numProcessors;
+ #endif
+
+ for (int i = 0; i < numProps; i++)
+ {
+ UString name = names[i];
+ name.MakeUpper();
+ if (name.IsEmpty())
+ return E_INVALIDARG;
+ const PROPVARIANT &prop = values[i];
+ if (name[0] == L'X')
+ {
+ UInt32 level = 9;
+ RINOK(ParsePropValue(name.Mid(1), prop, level));
+ _level = level;
+ }
+ else if (name[0] == L'D')
+ {
+ UInt32 dicSize = kDicSizeX5;
+ RINOK(ParsePropDictionaryValue(name.Mid(1), prop, dicSize));
+ _dicSize = dicSize;
+ }
+ else if (name.Left(4) == L"PASS")
+ {
+ UInt32 num = kNumPassesX9;
+ RINOK(ParsePropValue(name.Mid(4), prop, num));
+ _numPasses = num;
+ }
+ else if (name.Left(2) == L"MT")
+ {
+ #ifdef COMPRESS_MT
+ RINOK(ParseMtProp(name.Mid(2), prop, numProcessors, _numThreads));
+ #endif
+ }
+ else
+ return E_INVALIDARG;
+ }
+ return S_OK;
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+#ifndef EXTRACT_ONLY
+static IOutArchive *CreateArcOut() { return new CHandler; }
+#else
+#define CreateArcOut 0
+#endif
+
+static CArcInfo g_ArcInfo =
+ { L"BZip2", L"bz2 bzip2 tbz2 tbz", L"* * .tar .tar", 2, { 'B', 'Z', 'h' }, 3, true, CreateArc, CreateArcOut };
+
+REGISTER_ARC(BZip2)
+
+}}
diff --git a/CPP/7zip/Archive/Cab/CabBlockInStream.cpp b/CPP/7zip/Archive/Cab/CabBlockInStream.cpp
index 308616b8..12c73eb5 100755
--- a/CPP/7zip/Archive/Cab/CabBlockInStream.cpp
+++ b/CPP/7zip/Archive/Cab/CabBlockInStream.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../../C/Alloc.h"
-}
#include "Common/Defs.h"
diff --git a/CPP/7zip/Archive/Cab/CabIn.cpp b/CPP/7zip/Archive/Cab/CabIn.cpp
index 2b0a426b..afc0faed 100755
--- a/CPP/7zip/Archive/Cab/CabIn.cpp
+++ b/CPP/7zip/Archive/Cab/CabIn.cpp
@@ -57,7 +57,7 @@ void CInArchive::ReadOtherArchive(COtherArchive &oa)
oa.DiskName = SafeReadName();
}
-void CInArchive::Skeep(size_t size)
+void CInArchive::Skip(size_t size)
{
while (size-- != 0)
ReadByte();
@@ -104,7 +104,7 @@ HRESULT CInArchive::Open2(IInStream *stream,
ai.PerFolderAreaSize = ReadByte();
ai.PerDataBlockAreaSize = ReadByte();
- Skeep(ai.PerCabinetAreaSize);
+ Skip(ai.PerCabinetAreaSize);
}
{
@@ -124,7 +124,7 @@ HRESULT CInArchive::Open2(IInStream *stream,
folder.CompressionTypeMajor = ReadByte();
folder.CompressionTypeMinor = ReadByte();
- Skeep(ai.PerFolderAreaSize);
+ Skip(ai.PerFolderAreaSize);
database.Folders.Add(folder);
}
diff --git a/CPP/7zip/Archive/Cab/CabIn.h b/CPP/7zip/Archive/Cab/CabIn.h
index 197017b9..c9cfcbdd 100755
--- a/CPP/7zip/Archive/Cab/CabIn.h
+++ b/CPP/7zip/Archive/Cab/CabIn.h
@@ -149,7 +149,7 @@ class CInArchive
UInt16 ReadUInt16();
UInt32 ReadUInt32();
AString SafeReadName();
- void Skeep(size_t size);
+ void Skip(size_t size);
void ReadOtherArchive(COtherArchive &oa);
HRESULT Open2(IInStream *inStream,
diff --git a/CPP/7zip/Archive/Chm/ChmIn.cpp b/CPP/7zip/Archive/Chm/ChmIn.cpp
index 1379b1fd..cc571937 100755
--- a/CPP/7zip/Archive/Chm/ChmIn.cpp
+++ b/CPP/7zip/Archive/Chm/ChmIn.cpp
@@ -2,13 +2,11 @@
#include "StdAfx.h"
-#include "Common/StringConvert.h"
-#include "Common/MyCom.h"
-#include "Common/UTFConvert.h"
#include "Common/IntToString.h"
-#include "Windows/Defs.h"
+#include "Common/UTFConvert.h"
#include "../../Common/LimitedStreams.h"
+
#include "ChmIn.h"
namespace NArchive{
@@ -96,9 +94,8 @@ UString CMethodInfo::GetName() const
if (IsLzx())
{
s = L"LZX:";
- UInt32 numDictBits = LzxInfo.GetNumDictBits();
- wchar_t temp[32];
- ConvertUInt64ToString(numDictBits, temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(LzxInfo.GetNumDictBits(), temp);
s += temp;
}
else
@@ -111,7 +108,7 @@ UString CMethodInfo::GetName() const
s2 = GetGuidString();
if (ControlData.GetCapacity() > 0)
{
- s2 += ":";
+ s2 += ':';
for (size_t i = 0; i < ControlData.GetCapacity(); i++)
PrintByte(ControlData[i], s2);
}
@@ -141,7 +138,7 @@ UString CSectionInfo::GetMethodName() const
for (int i = 0; i < Methods.Size(); i++)
{
if (i != 0)
- s += L" ";
+ s += L' ';
s += Methods[i].GetName();
}
return s;
@@ -155,7 +152,7 @@ Byte CInArchive::ReadByte()
return b;
}
-void CInArchive::Skeep(size_t size)
+void CInArchive::Skip(size_t size)
{
while (size-- != 0)
ReadByte();
@@ -221,7 +218,7 @@ void CInArchive::ReadString(int size, AString &s)
char c = (char)ReadByte();
if (c == 0)
{
- Skeep(size);
+ Skip(size);
return;
}
s += c;
@@ -236,7 +233,7 @@ void CInArchive::ReadUString(int size, UString &s)
wchar_t c = ReadUInt16();
if (c == 0)
{
- Skeep(2 * size);
+ Skip(2 * size);
return;
}
s += c;
@@ -372,12 +369,12 @@ HRESULT CInArchive::OpenChm(IInStream *inStream, CDatabase &database)
RINOK(ReadDirEntry(database));
numItems++;
}
- Skeep(quickrefLength - 2);
+ Skip(quickrefLength - 2);
if (ReadUInt16() != numItems)
return S_FALSE;
}
else
- Skeep(dirChunkSize - 4);
+ Skip(dirChunkSize - 4);
}
return S_OK;
}
@@ -579,7 +576,7 @@ HRESULT CInArchive::OpenHelp2(IInStream *inStream, CDatabase &database)
}
numItems++;
}
- Skeep(quickrefLength - 2);
+ Skip(quickrefLength - 2);
if (ReadUInt16() != numItems)
return S_FALSE;
if (numItems > numDirEntries)
@@ -587,7 +584,7 @@ HRESULT CInArchive::OpenHelp2(IInStream *inStream, CDatabase &database)
numDirEntries -= numItems;
}
else
- Skeep(dirChunkSize - 4);
+ Skip(dirChunkSize - 4);
}
return numDirEntries == 0 ? S_OK : S_FALSE;
}
diff --git a/CPP/7zip/Archive/Chm/ChmIn.h b/CPP/7zip/Archive/Chm/ChmIn.h
index 943336cb..4719a484 100755
--- a/CPP/7zip/Archive/Chm/ChmIn.h
+++ b/CPP/7zip/Archive/Chm/ChmIn.h
@@ -3,10 +3,12 @@
#ifndef __ARCHIVE_CHM_IN_H
#define __ARCHIVE_CHM_IN_H
-#include "Common/MyString.h"
#include "Common/Buffer.h"
+#include "Common/MyString.h"
+
#include "../../IStream.h"
#include "../../Common/InBuffer.h"
+
#include "ChmHeader.h"
namespace NArchive {
@@ -215,7 +217,7 @@ class CInArchive
Byte ReadByte();
void ReadBytes(Byte *data, UInt32 size);
- void Skeep(size_t size);
+ void Skip(size_t size);
UInt16 ReadUInt16();
UInt32 ReadUInt32();
UInt64 ReadUInt64();
diff --git a/CPP/7zip/Archive/Com/ComHandler.cpp b/CPP/7zip/Archive/Com/ComHandler.cpp
index 8b46976c..287f6156 100755
--- a/CPP/7zip/Archive/Com/ComHandler.cpp
+++ b/CPP/7zip/Archive/Com/ComHandler.cpp
@@ -3,8 +3,15 @@
#include "StdAfx.h"
#include "Common/ComTry.h"
+
#include "Windows/PropVariant.h"
+
+#include "../../Common/LimitedStreams.h"
+#include "../../Common/ProgressUtils.h"
#include "../../Common/StreamUtils.h"
+
+#include "../../Compress/CopyCoder.h"
+
#include "ComHandler.h"
namespace NArchive {
@@ -15,16 +22,15 @@ STATPROPSTG kProps[] =
{ NULL, kpidPath, VT_BSTR},
{ NULL, kpidIsDir, VT_BOOL},
{ NULL, kpidSize, VT_UI8},
- // { NULL, kpidAttributes, VT_UI4},
{ NULL, kpidPackSize, VT_UI8},
{ NULL, kpidCTime, VT_FILETIME},
{ NULL, kpidMTime, VT_FILETIME}
};
-
STATPROPSTG kArcProps[] =
{
- { NULL, kpidClusterSize, VT_UI4}
+ { NULL, kpidClusterSize, VT_UI4},
+ { NULL, kpidSectorSize, VT_UI4}
};
IMP_IInArchive_Props
@@ -37,6 +43,7 @@ STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
switch(propID)
{
case kpidClusterSize: prop = (UInt32)1 << _db.SectorSizeBits; break;
+ case kpidSectorSize: prop = (UInt32)1 << _db.MiniSectorSizeBits; break;
}
prop.Detach(value);
return S_OK;
@@ -52,33 +59,12 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
switch(propID)
{
- case kpidPath:
- {
- UString name = _db.GetItemPath(index);
- prop = name;
- break;
- }
+ case kpidPath: prop = _db.GetItemPath(index); break;
case kpidIsDir: prop = item.IsDir(); break;
case kpidCTime: prop = item.CTime; break;
case kpidMTime: prop = item.MTime; break;
- /*
- case kpidAttributes:
- prop = item.Falgs;
- break;
- */
- case kpidPackSize:
- if (!item.IsDir())
- {
- int numBits = _db.IsLargeStream(item.Size) ?
- _db.SectorSizeBits :
- _db.MiniSectorSizeBits;
- prop = (item.Size + ((UInt64)1 << numBits) - 1) >> numBits << numBits;
- break;
- }
- case kpidSize:
- if (!item.IsDir())
- prop = (UInt64)item.Size;
- break;
+ case kpidPackSize: if (!item.IsDir()) prop = _db.GetItemPackSize(item.Size); break;
+ case kpidSize: if (!item.IsDir()) prop = item.Size; break;
}
prop.Detach(value);
return S_OK;
@@ -93,7 +79,7 @@ STDMETHODIMP CHandler::Open(IInStream *inStream,
Close();
try
{
- if (OpenArchive(inStream, _db) != S_OK)
+ if (_db.Open(inStream) != S_OK)
return S_FALSE;
_stream = inStream;
}
@@ -129,25 +115,29 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
}
RINOK(extractCallback->SetTotal(totalSize));
- UInt64 currentTotalSize = 0, currentItemSize = 0;
+ UInt64 totalPackSize;
+ totalSize = totalPackSize = 0;
- CByteBuffer sect;
- sect.SetCapacity((UInt32)1 << _db.SectorSizeBits);
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
- for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ for (i = 0; i < numItems; i++)
{
- RINOK(extractCallback->SetCompleted(&currentTotalSize));
+ lps->InSize = totalPackSize;
+ lps->OutSize = totalSize;
+ RINOK(lps->SetCur());
Int32 index = allFilesMode ? i : indices[i];
const CItem &item = _db.Items[_db.Refs[index].Did];
- currentItemSize = 0;
- if (!item.IsDir())
- currentItemSize = item.Size;
- CMyComPtr<ISequentialOutStream> realOutStream;
+ CMyComPtr<ISequentialOutStream> outStream;
Int32 askMode = testMode ?
NArchive::NExtract::NAskMode::kTest :
NArchive::NExtract::NAskMode::kExtract;
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
if (item.IsDir())
{
@@ -155,75 +145,31 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
continue;
}
- if (!testMode && (!realOutStream))
+
+ totalPackSize += _db.GetItemPackSize(item.Size);
+ totalSize += item.Size;
+
+ if (!testMode && (!outStream))
continue;
RINOK(extractCallback->PrepareOperation(askMode));
Int32 res = NArchive::NExtract::NOperationResult::kDataError;
+ CMyComPtr<ISequentialInStream> inStream;
+ HRESULT hres = GetStream(index, &inStream);
+ if (hres == S_FALSE)
+ res = NArchive::NExtract::NOperationResult::kDataError;
+ else if (hres == E_NOTIMPL)
+ res = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
+ else
{
- UInt32 sid = item.Sid;
- UInt64 prev = 0;
- for (UInt64 pos = 0;;)
+ RINOK(hres);
+ if (inStream)
{
- if (sid == NFatID::kEndOfChain)
- {
- if (pos != item.Size)
- break;
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ if (copyCoderSpec->TotalSize == item.Size)
res = NArchive::NExtract::NOperationResult::kOK;
- break;
- }
- if (pos >= item.Size)
- break;
-
- UInt64 offset;
- UInt32 size;
-
- if (_db.IsLargeStream(item.Size))
- {
- if (pos - prev > (1 << 20))
- {
- UInt64 processed = currentTotalSize + pos;
- RINOK(extractCallback->SetCompleted(&processed));
- prev = pos;
- }
- size = 1 << _db.SectorSizeBits;
- offset = ((UInt64)sid + 1) << _db.SectorSizeBits;
- if (sid >= _db.FatSize)
- break;
- sid = _db.Fat[sid];
- }
- else
- {
- int subBits = (_db.SectorSizeBits - _db.MiniSectorSizeBits);
- UInt32 fid = sid >> subBits;
- if (fid >= _db.NumSectorsInMiniStream)
- break;
- size = 1 << _db.MiniSectorSizeBits;
- offset = (((UInt64)_db.MiniSids[fid] + 1) << _db.SectorSizeBits) +
- ((sid & ((1 << subBits) - 1)) << _db.MiniSectorSizeBits);
- if (sid >= _db.MatSize)
- break;
- sid = _db.Mat[sid];
- }
-
- // last sector can be smaller than sector size (it can contain requied data only).
- UInt64 rem = item.Size - pos;
- if (size > rem)
- size = (UInt32)rem;
-
- RINOK(_stream->Seek(offset, STREAM_SEEK_SET, NULL));
- size_t realProcessedSize = size;
- RINOK(ReadStream(_stream, sect, &realProcessedSize));
- if (realProcessedSize != size)
- break;
-
- if (realOutStream)
- {
- RINOK(WriteStream(realOutStream, sect, size));
- }
- pos += size;
}
}
- realOutStream.Release();
+ outStream.Release();
RINOK(extractCallback->SetOperationResult(res));
}
return S_OK;
@@ -236,4 +182,58 @@ STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
return S_OK;
}
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ *stream = 0;
+ const CItem &item = _db.Items[_db.Refs[index].Did];
+ CClusterInStream *streamSpec = new CClusterInStream;
+ CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
+ streamSpec->Stream = _stream;
+ streamSpec->StartOffset = 0;
+
+ bool isLargeStream = _db.IsLargeStream(item.Size);
+ int bsLog = isLargeStream ? _db.SectorSizeBits : _db.MiniSectorSizeBits;
+ streamSpec->BlockSizeLog = bsLog;
+ streamSpec->Size = item.Size;
+
+ UInt32 clusterSize = (UInt32)1 << bsLog;
+ UInt64 numClusters64 = (item.Size + clusterSize - 1) >> bsLog;
+ if (numClusters64 >= ((UInt32)1 << 31))
+ return E_NOTIMPL;
+ streamSpec->Vector.Reserve((int)numClusters64);
+ UInt32 sid = item.Sid;
+ UInt64 size = item.Size;
+
+ if (size != 0)
+ {
+ for (;; size -= clusterSize)
+ {
+ if (isLargeStream)
+ {
+ if (sid >= _db.FatSize)
+ return S_FALSE;
+ streamSpec->Vector.Add(sid + 1);
+ sid = _db.Fat[sid];
+ }
+ else
+ {
+ UInt64 val;
+ if (sid >= _db.MatSize || !_db.GetMiniCluster(sid, val) || val >= (UInt64)1 << 32)
+ return S_FALSE;
+ streamSpec->Vector.Add((UInt32)val);
+ sid = _db.Mat[sid];
+ }
+ if (size <= clusterSize)
+ break;
+ }
+ }
+ if (sid != NFatID::kEndOfChain)
+ return S_FALSE;
+ RINOK(streamSpec->InitAndSeek());
+ *stream = streamTemp.Detach();
+ return S_OK;
+ COM_TRY_END
+}
+
}}
diff --git a/CPP/7zip/Archive/Com/ComHandler.h b/CPP/7zip/Archive/Com/ComHandler.h
index 89bc98d0..f2b7de96 100755
--- a/CPP/7zip/Archive/Com/ComHandler.h
+++ b/CPP/7zip/Archive/Com/ComHandler.h
@@ -12,15 +12,15 @@ namespace NCom {
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
-public:
- MY_UNKNOWN_IMP1(IInArchive)
- INTERFACE_IInArchive(;)
-
-private:
CMyComPtr<IInStream> _stream;
CDatabase _db;
+public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
}}
diff --git a/CPP/7zip/Archive/Com/ComIn.cpp b/CPP/7zip/Archive/Com/ComIn.cpp
index 74e601c1..8f622122 100755
--- a/CPP/7zip/Archive/Com/ComIn.cpp
+++ b/CPP/7zip/Archive/Com/ComIn.cpp
@@ -2,19 +2,19 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../../C/Alloc.h"
-}
-
#include "../../../../C/CpuArch.h"
+#include "Common/IntToString.h"
#include "Common/MyCom.h"
+
#include "../../Common/StreamUtils.h"
-#include "Common/IntToString.h"
#include "ComIn.h"
+#define Get16(p) GetUi16(p)
+#define Get32(p) GetUi32(p)
+
namespace NArchive{
namespace NCom{
@@ -50,31 +50,40 @@ static HRESULT ReadIDs(IInStream *inStream, Byte *buf, int sectorSizeBits, UInt3
RINOK(ReadSector(inStream, buf, sectorSizeBits, sid));
UInt32 sectorSize = (UInt32)1 << sectorSizeBits;
for (UInt32 t = 0; t < sectorSize; t += 4)
- *dest++ = GetUi32(buf + t);
+ *dest++ = Get32(buf + t);
return S_OK;
}
static void GetFileTimeFromMem(const Byte *p, FILETIME *ft)
{
- ft->dwLowDateTime = GetUi32(p);
- ft->dwHighDateTime = GetUi32(p + 4);
+ ft->dwLowDateTime = Get32(p);
+ ft->dwHighDateTime = Get32(p + 4);
}
-static void ReadItem(Byte *p, CItem &item, bool mode64bit)
+void CItem::Parse(const Byte *p, bool mode64bit)
{
- memcpy(item.Name, p, 64);
- // item.NameSize = GetUi16(p + 64);
- item.Type = p[66];
- item.LeftDid = GetUi32(p + 68);
- item.RightDid = GetUi32(p + 72);
- item.SonDid = GetUi32(p + 76);
- // item.Flags = GetUi32(p + 96);
- GetFileTimeFromMem(p + 100, &item.CTime);
- GetFileTimeFromMem(p + 108, &item.MTime);
- item.Sid = GetUi32(p + 116);
- item.Size = GetUi32(p + 120);
+ memcpy(Name, p, kNameSizeMax);
+ // NameSize = Get16(p + 64);
+ Type = p[66];
+ LeftDid = Get32(p + 68);
+ RightDid = Get32(p + 72);
+ SonDid = Get32(p + 76);
+ // Flags = Get32(p + 96);
+ GetFileTimeFromMem(p + 100, &CTime);
+ GetFileTimeFromMem(p + 108, &MTime);
+ Sid = Get32(p + 116);
+ Size = Get32(p + 120);
if (mode64bit)
- item.Size |= ((UInt64)GetUi32(p + 124) << 32);
+ Size |= ((UInt64)Get32(p + 124) << 32);
+}
+
+void CDatabase::Clear()
+{
+ Fat.Free();
+ MiniSids.Free();
+ Mat.Free();
+ Items.Clear();
+ Refs.Clear();
}
static const UInt32 kNoDid = 0xFFFFFFFF;
@@ -106,13 +115,6 @@ HRESULT CDatabase::AddNode(int parent, UInt32 did)
static const char kCharOpenBracket = '[';
static const char kCharCloseBracket = ']';
-UString DWORDToString(UInt32 val)
-{
- wchar_t buf[32];
- ConvertUInt64ToString(val, buf);
- return buf;
-}
-
static UString CompoundNameToFileName(const UString &s)
{
UString res;
@@ -122,7 +124,9 @@ static UString CompoundNameToFileName(const UString &s)
if (c < 0x20)
{
res += kCharOpenBracket;
- res += DWORDToString(c);
+ wchar_t buf[32];
+ ConvertUInt32ToString(c, buf);
+ res += buf;
res += kCharCloseBracket;
}
else
@@ -201,31 +205,30 @@ UString CDatabase::GetItemPath(UInt32 index) const
return s;
}
-HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
+HRESULT CDatabase::Open(IInStream *inStream)
{
static const UInt32 kHeaderSize = 512;
Byte p[kHeaderSize];
RINOK(ReadStream_FALSE(inStream, p, kHeaderSize));
if (memcmp(p, kSignature, kSignatureSize) != 0)
return S_FALSE;
- UInt16 majorVer = GetUi16(p + 0x1A);
- if (majorVer > 4)
+ if (Get16(p + 0x1A) > 4) // majorVer
return S_FALSE;
- if (GetUi16(p + 0x1C) != 0xFFFE)
+ if (Get16(p + 0x1C) != 0xFFFE)
return S_FALSE;
- UInt16 sectorSizeBits = GetUi16(p + 0x1E);
+ int sectorSizeBits = Get16(p + 0x1E);
bool mode64bit = (sectorSizeBits >= 12);
- UInt16 miniSectorSizeBits = GetUi16(p + 0x20);
- db.SectorSizeBits = sectorSizeBits;
- db.MiniSectorSizeBits = miniSectorSizeBits;
+ int miniSectorSizeBits = Get16(p + 0x20);
+ SectorSizeBits = sectorSizeBits;
+ MiniSectorSizeBits = miniSectorSizeBits;
if (sectorSizeBits > 28 || miniSectorSizeBits > 28 ||
sectorSizeBits < 7 || miniSectorSizeBits < 2 || miniSectorSizeBits > sectorSizeBits)
return S_FALSE;
- UInt32 numSectorsForFAT = GetUi32(p + 0x2C);
- db.LongStreamMinSize = GetUi32(p + 0x38);
+ UInt32 numSectorsForFAT = Get32(p + 0x2C);
+ LongStreamMinSize = Get32(p + 0x38);
- UInt32 sectSize = (UInt32)1 << (int)(sectorSizeBits);
+ UInt32 sectSize = (UInt32)1 << (int)sectorSizeBits;
CByteBuffer sect;
sect.SetCapacity(sectSize);
@@ -235,11 +238,11 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
UInt32 numFatItems = numSectorsForFAT << ssb2;
if ((numFatItems >> ssb2) != numSectorsForFAT)
return S_FALSE;
- db.FatSize = numFatItems;
+ FatSize = numFatItems;
{
CUInt32Buf bat;
- UInt32 numSectorsForBat = GetUi32(p + 0x48);
+ UInt32 numSectorsForBat = Get32(p + 0x48);
const UInt32 kNumHeaderBatItems = 109;
UInt32 numBatItems = kNumHeaderBatItems + (numSectorsForBat << ssb2);
if (numBatItems < kNumHeaderBatItems || ((numBatItems - kNumHeaderBatItems) >> ssb2) != numSectorsForBat)
@@ -248,8 +251,8 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
return S_FALSE;
UInt32 i;
for (i = 0; i < kNumHeaderBatItems; i++)
- bat[i] = GetUi32(p + 0x4c + i * 4);
- UInt32 sid = GetUi32(p + 0x44);
+ bat[i] = Get32(p + 0x4c + i * 4);
+ UInt32 sid = Get32(p + 0x44);
for (UInt32 s = 0; s < numSectorsForBat; s++)
{
RINOK(ReadIDs(inStream, sect, sectorSizeBits, sid, bat + i));
@@ -258,7 +261,7 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
}
numBatItems = i;
- if (!db.Fat.Allocate(numFatItems))
+ if (!Fat.Allocate(numFatItems))
return S_FALSE;
UInt32 j = 0;
@@ -266,33 +269,33 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
{
if (j >= numBatItems)
return S_FALSE;
- RINOK(ReadIDs(inStream, sect, sectorSizeBits, bat[j], db.Fat + i));
+ RINOK(ReadIDs(inStream, sect, sectorSizeBits, bat[j], Fat + i));
}
}
UInt32 numMatItems;
{
- UInt32 numSectorsForMat = GetUi32(p + 0x40);
+ UInt32 numSectorsForMat = Get32(p + 0x40);
numMatItems = (UInt32)numSectorsForMat << ssb2;
if ((numMatItems >> ssb2) != numSectorsForMat)
return S_FALSE;
- if (!db.Mat.Allocate(numMatItems))
+ if (!Mat.Allocate(numMatItems))
return S_FALSE;
UInt32 i;
- UInt32 sid = GetUi32(p + 0x3C);
+ UInt32 sid = Get32(p + 0x3C);
for (i = 0; i < numMatItems; i += numSidsInSec)
{
- RINOK(ReadIDs(inStream, sect, sectorSizeBits, sid, db.Mat + i));
+ RINOK(ReadIDs(inStream, sect, sectorSizeBits, sid, Mat + i));
if (sid >= numFatItems)
return S_FALSE;
- sid = db.Fat[sid];
+ sid = Fat[sid];
}
if (sid != NFatID::kEndOfChain)
return S_FALSE;
}
{
- UInt32 sid = GetUi32(p + 0x30);
+ UInt32 sid = Get32(p + 0x30);
for (;;)
{
if (sid >= numFatItems)
@@ -301,16 +304,16 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
for (UInt32 i = 0; i < sectSize; i += 128)
{
CItem item;
- ReadItem(sect + i, item, mode64bit);
- db.Items.Add(item);
+ item.Parse(sect + i, mode64bit);
+ Items.Add(item);
}
- sid = db.Fat[sid];
+ sid = Fat[sid];
if (sid == NFatID::kEndOfChain)
break;
}
}
- CItem root = db.Items[0];
+ CItem root = Items[0];
{
UInt32 numSectorsInMiniStream;
@@ -320,19 +323,18 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
return S_FALSE;
numSectorsInMiniStream = (UInt32)numSatSects64;
}
- db.NumSectorsInMiniStream = numSectorsInMiniStream;
- if (!db.MiniSids.Allocate(numSectorsInMiniStream))
+ NumSectorsInMiniStream = numSectorsInMiniStream;
+ if (!MiniSids.Allocate(numSectorsInMiniStream))
return S_FALSE;
{
UInt64 matSize64 = (root.Size + ((UInt64)1 << miniSectorSizeBits) - 1) >> miniSectorSizeBits;
if (matSize64 > NFatID::kMaxValue)
return S_FALSE;
- db.MatSize = (UInt32)matSize64;
- if (numMatItems < db.MatSize)
+ MatSize = (UInt32)matSize64;
+ if (numMatItems < MatSize)
return S_FALSE;
}
-
UInt32 sid = root.Sid;
for (UInt32 i = 0; ; i++)
{
@@ -344,14 +346,14 @@ HRESULT OpenArchive(IInStream *inStream, CDatabase &db)
}
if (i >= numSectorsInMiniStream)
return S_FALSE;
- db.MiniSids[i] = sid;
+ MiniSids[i] = sid;
if (sid >= numFatItems)
return S_FALSE;
- sid = db.Fat[sid];
+ sid = Fat[sid];
}
}
- return db.AddNode(-1, root.SonDid);
+ return AddNode(-1, root.SonDid);
}
}}
diff --git a/CPP/7zip/Archive/Com/ComIn.h b/CPP/7zip/Archive/Com/ComIn.h
index 081c6aaa..05fc7387 100755
--- a/CPP/7zip/Archive/Com/ComIn.h
+++ b/CPP/7zip/Archive/Com/ComIn.h
@@ -57,6 +57,8 @@ struct CItem
bool IsEmpty() const { return Type == NItemType::kEmpty; }
bool IsDir() const { return Type == NItemType::kStorage || Type == NItemType::kRootStorage; }
+
+ void Parse(const Byte *p, bool mode64bit);
};
struct CRef
@@ -67,15 +69,15 @@ struct CRef
class CDatabase
{
-public:
+ UInt32 NumSectorsInMiniStream;
+ CUInt32Buf MiniSids;
+
HRESULT AddNode(int parent, UInt32 did);
+public:
CUInt32Buf Fat;
UInt32 FatSize;
- CUInt32Buf MiniSids;
- UInt32 NumSectorsInMiniStream;
-
CUInt32Buf Mat;
UInt32 MatSize;
@@ -86,20 +88,29 @@ public:
int SectorSizeBits;
int MiniSectorSizeBits;
- void Clear()
+ void Clear();
+ bool IsLargeStream(UInt64 size) const { return size >= LongStreamMinSize; }
+ UString GetItemPath(UInt32 index) const;
+
+ UInt64 GetItemPackSize(UInt64 size) const
{
- Fat.Free();
- MiniSids.Free();
- Mat.Free();
- Items.Clear();
- Refs.Clear();
+ UInt64 mask = ((UInt64)1 << (IsLargeStream(size) ? SectorSizeBits : MiniSectorSizeBits)) - 1;
+ return (size + mask) & ~mask;
}
- bool IsLargeStream(UInt64 size) { return size >= LongStreamMinSize; }
- UString GetItemPath(UInt32 index) const;
+ bool GetMiniCluster(UInt32 sid, UInt64 &res) const
+ {
+ int subBits = SectorSizeBits - MiniSectorSizeBits;
+ UInt32 fid = sid >> subBits;
+ if (fid >= NumSectorsInMiniStream)
+ return false;
+ res = (((UInt64)MiniSids[fid] + 1) << subBits) + (sid & ((1 << subBits) - 1));
+ return true;
+ }
+
+ HRESULT Open(IInStream *inStream);
};
-HRESULT OpenArchive(IInStream *inStream, CDatabase &database);
}}
diff --git a/CPP/7zip/Archive/Common/HandlerOut.cpp b/CPP/7zip/Archive/Common/HandlerOut.cpp
index 76739e94..46f835ef 100755
--- a/CPP/7zip/Archive/Common/HandlerOut.cpp
+++ b/CPP/7zip/Archive/Common/HandlerOut.cpp
@@ -82,11 +82,11 @@ static const UInt32 kAlgorithmForHeaders = kLzmaAlgoX5;
static bool AreEqual(const UString &methodName, const wchar_t *s)
{ return (methodName.CompareNoCase(s) == 0); }
-static inline bool IsLZMAMethod(const UString &methodName)
+bool COneMethodInfo::IsLzma() const
{
return
- AreEqual(methodName, kLZMAMethodName) ||
- AreEqual(methodName, kLZMA2MethodName);
+ AreEqual(MethodName, kLZMAMethodName) ||
+ AreEqual(MethodName, kLZMA2MethodName);
}
static inline bool IsBZip2Method(const UString &methodName)
@@ -109,8 +109,12 @@ struct CNameToPropID
const wchar_t *Name;
};
-CNameToPropID g_NameToPropID[] =
+static CNameToPropID g_NameToPropID[] =
{
+ { NCoderPropID::kBlockSize, VT_UI4, L"C" },
+ { NCoderPropID::kDictionarySize, VT_UI4, L"D" },
+ { NCoderPropID::kUsedMemorySize, VT_UI4, L"MEM" },
+
{ NCoderPropID::kOrder, VT_UI4, L"O" },
{ NCoderPropID::kPosStateBits, VT_UI4, L"PB" },
{ NCoderPropID::kLitContextBits, VT_UI4, L"LC" },
@@ -122,7 +126,8 @@ CNameToPropID g_NameToPropID[] =
{ NCoderPropID::kMatchFinderCycles, VT_UI4, L"mc" },
{ NCoderPropID::kAlgorithm, VT_UI4, L"a" },
{ NCoderPropID::kMatchFinder, VT_BSTR, L"mf" },
- { NCoderPropID::kNumThreads, VT_UI4, L"mt" }
+ { NCoderPropID::kNumThreads, VT_UI4, L"mt" },
+ { NCoderPropID::kDefaultProp, VT_UI4, L"" }
};
static bool ConvertProperty(PROPVARIANT srcProp, VARTYPE varType, NCOM::CPropVariant &destProp)
@@ -154,7 +159,7 @@ static bool ConvertProperty(PROPVARIANT srcProp, VARTYPE varType, NCOM::CPropVar
return false;
}
-static int FindPropIdFromStringName(const UString &name)
+static int FindPropIdExact(const UString &name)
{
for (int i = 0; i < sizeof(g_NameToPropID) / sizeof(g_NameToPropID[0]); i++)
if (name.CompareNoCase(g_NameToPropID[i].Name) == 0)
@@ -162,16 +167,26 @@ static int FindPropIdFromStringName(const UString &name)
return -1;
}
-static void SetOneMethodProp(COneMethodInfo &oneMethodInfo, PROPID propID,
- const NWindows::NCOM::CPropVariant &value)
+static int FindPropIdStart(const UString &name)
+{
+ for (int i = 0; i < sizeof(g_NameToPropID) / sizeof(g_NameToPropID[0]); i++)
+ {
+ UString t = g_NameToPropID[i].Name;
+ if (t.CompareNoCase(name.Left(t.Length())) == 0)
+ return i;
+ }
+ return -1;
+}
+
+static void SetMethodProp(COneMethodInfo &m, PROPID propID, const NCOM::CPropVariant &value)
{
- for (int j = 0; j < oneMethodInfo.Props.Size(); j++)
- if (oneMethodInfo.Props[j].Id == propID)
+ for (int j = 0; j < m.Props.Size(); j++)
+ if (m.Props[j].Id == propID)
return;
CProp prop;
prop.Id = propID;
prop.Value = value;
- oneMethodInfo.Props.Add(prop);
+ m.Props.Add(prop);
}
void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
@@ -184,7 +199,7 @@ void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
if (oneMethodInfo.MethodName.IsEmpty())
oneMethodInfo.MethodName = kDefaultMethodName;
- if (IsLZMAMethod(oneMethodInfo.MethodName))
+ if (oneMethodInfo.IsLzma())
{
UInt32 dicSize =
(level >= 9 ? kLzmaDicSizeX9 :
@@ -205,12 +220,12 @@ void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
(level >= 5 ? kLzmaMatchFinderX5 :
kLzmaMatchFinderX1);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kDictionarySize, dicSize);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kAlgorithm, algo);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumFastBytes, fastBytes);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kMatchFinder, matchFinder);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kDictionarySize, dicSize);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kAlgorithm, algo);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumFastBytes, fastBytes);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kMatchFinder, matchFinder);
#ifdef COMPRESS_MT
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumThreads, numThreads);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumThreads, numThreads);
#endif
}
else if (IsDeflateMethod(oneMethodInfo.MethodName))
@@ -229,9 +244,9 @@ void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
(level >= 5 ? kDeflateAlgoX5 :
kDeflateAlgoX1);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kAlgorithm, algo);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumFastBytes, fastBytes);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumPasses, numPasses);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kAlgorithm, algo);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumFastBytes, fastBytes);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumPasses, numPasses);
}
else if (IsBZip2Method(oneMethodInfo.MethodName))
{
@@ -245,10 +260,10 @@ void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
(level >= 3 ? kBZip2DicSizeX3 :
kBZip2DicSizeX1));
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumPasses, numPasses);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kDictionarySize, dicSize);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumPasses, numPasses);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kDictionarySize, dicSize);
#ifdef COMPRESS_MT
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kNumThreads, numThreads);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kNumThreads, numThreads);
#endif
}
else if (IsPpmdMethod(oneMethodInfo.MethodName))
@@ -265,8 +280,8 @@ void COutHandler::SetCompressionMethod2(COneMethodInfo &oneMethodInfo
(level >= 5 ? kPpmdOrderX5 :
kPpmdOrderX1)));
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kUsedMemorySize, useMemSize);
- SetOneMethodProp(oneMethodInfo, NCoderPropID::kOrder, order);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kUsedMemorySize, useMemSize);
+ SetMethodProp(oneMethodInfo, NCoderPropID::kOrder, order);
}
}
@@ -316,25 +331,22 @@ static void SplitParam(const UString &param, UString &name, UString &value)
HRESULT COutHandler::SetParam(COneMethodInfo &oneMethodInfo, const UString &name, const UString &value)
{
CProp prop;
- if (name.CompareNoCase(L"D") == 0 ||
- name.CompareNoCase(L"MEM") == 0)
+ int index = FindPropIdExact(name);
+ if (index < 0)
+ return E_INVALIDARG;
+ const CNameToPropID &nameToPropID = g_NameToPropID[index];
+ prop.Id = nameToPropID.PropID;
+
+ if (prop.Id == NCoderPropID::kBlockSize ||
+ prop.Id == NCoderPropID::kDictionarySize ||
+ prop.Id == NCoderPropID::kUsedMemorySize)
{
UInt32 dicSize;
RINOK(ParsePropDictionaryValue(value, dicSize));
- prop.Id = (name.CompareNoCase(L"D") == 0) ?
- NCoderPropID::kDictionarySize :
- NCoderPropID::kUsedMemorySize;
prop.Value = dicSize;
}
else
{
- int index = FindPropIdFromStringName(name);
- if (index < 0)
- return E_INVALIDARG;
-
- const CNameToPropID &nameToPropID = g_NameToPropID[index];
- prop.Id = nameToPropID.PropID;
-
NCOM::CPropVariant propValue;
if (nameToPropID.VarType == VT_BSTR)
@@ -465,7 +477,7 @@ void COutHandler::Init()
WriteMTime = true;
#ifdef COMPRESS_MT
- _numThreads = NWindows::NSystem::GetNumberOfProcessors();
+ _numThreads = NSystem::GetNumberOfProcessors();
#endif
_level = 5;
@@ -576,35 +588,26 @@ HRESULT COutHandler::SetProperty(const wchar_t *nameSpec, const PROPVARIANT &val
}
else
{
+ int index = FindPropIdStart(realName);
+ if (index < 0)
+ return E_INVALIDARG;
+ const CNameToPropID &nameToPropID = g_NameToPropID[index];
CProp prop;
- if (realName.Left(1).CompareNoCase(L"D") == 0)
- {
- UInt32 dicSize;
- RINOK(ParsePropDictionaryValue(realName.Mid(1), value, dicSize));
- prop.Id = NCoderPropID::kDictionarySize;
- prop.Value = dicSize;
- if (number <= mainDicMethodIndex)
- mainDicSize = dicSize;
- }
- else if (realName.Left(1).CompareNoCase(L"C") == 0)
- {
- UInt32 blockSize;
- RINOK(ParsePropDictionaryValue(realName.Mid(1), value, blockSize));
- prop.Id = NCoderPropID::kBlockSize;
- prop.Value = blockSize;
- }
- else if (realName.Left(3).CompareNoCase(L"MEM") == 0)
+ prop.Id = nameToPropID.PropID;
+
+ if (prop.Id == NCoderPropID::kBlockSize ||
+ prop.Id == NCoderPropID::kDictionarySize ||
+ prop.Id == NCoderPropID::kUsedMemorySize)
{
UInt32 dicSize;
- RINOK(ParsePropDictionaryValue(realName.Mid(3), value, dicSize));
- prop.Id = NCoderPropID::kUsedMemorySize;
+ RINOK(ParsePropDictionaryValue(realName.Mid(MyStringLen(nameToPropID.Name)), value, dicSize));
prop.Value = dicSize;
if (number <= mainDicMethodIndex)
mainDicSize = dicSize;
}
else
{
- int index = FindPropIdFromStringName(realName);
+ int index = FindPropIdExact(realName);
if (index < 0)
return E_INVALIDARG;
const CNameToPropID &nameToPropID = g_NameToPropID[index];
diff --git a/CPP/7zip/Archive/Common/HandlerOut.h b/CPP/7zip/Archive/Common/HandlerOut.h
index 89c81c1f..7ba22b24 100755
--- a/CPP/7zip/Archive/Common/HandlerOut.h
+++ b/CPP/7zip/Archive/Common/HandlerOut.h
@@ -12,6 +12,8 @@ struct COneMethodInfo
{
CObjectVector<CProp> Props;
UString MethodName;
+
+ bool IsLzma() const;
};
class COutHandler
diff --git a/CPP/7zip/Archive/Common/InStreamWithCRC.h b/CPP/7zip/Archive/Common/InStreamWithCRC.h
index c5ada6fe..0492a5f8 100755
--- a/CPP/7zip/Archive/Common/InStreamWithCRC.h
+++ b/CPP/7zip/Archive/Common/InStreamWithCRC.h
@@ -1,15 +1,13 @@
// InStreamWithCRC.h
-#ifndef __INSTREAMWITHCRC_H
-#define __INSTREAMWITHCRC_H
+#ifndef __IN_STREAM_WITH_CRC_H
+#define __IN_STREAM_WITH_CRC_H
+
+#include "../../../../C/7zCrc.h"
#include "../../../Common/MyCom.h"
-#include "../../IStream.h"
-extern "C"
-{
-#include "../../../../C/7zCrc.h"
-}
+#include "../../IStream.h"
class CSequentialInStreamWithCRC:
public ISequentialInStream,
diff --git a/CPP/7zip/Archive/Common/OutStreamWithCRC.cpp b/CPP/7zip/Archive/Common/OutStreamWithCRC.cpp
index 2ab2da66..f955c225 100755
--- a/CPP/7zip/Archive/Common/OutStreamWithCRC.cpp
+++ b/CPP/7zip/Archive/Common/OutStreamWithCRC.cpp
@@ -6,19 +6,13 @@
STDMETHODIMP COutStreamWithCRC::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
- UInt32 realProcessedSize;
- HRESULT result;
- if(!_stream)
- {
- realProcessedSize = size;
- result = S_OK;
- }
- else
- result = _stream->Write(data, size, &realProcessedSize);
+ HRESULT result = S_OK;
+ if (_stream)
+ result = _stream->Write(data, size, &size);
if (_calculate)
- _crc = CrcUpdate(_crc, data, realProcessedSize);
- _size += realProcessedSize;
- if(processedSize != NULL)
- *processedSize = realProcessedSize;
+ _crc = CrcUpdate(_crc, data, size);
+ _size += size;
+ if (processedSize != NULL)
+ *processedSize = size;
return result;
}
diff --git a/CPP/7zip/Archive/Common/OutStreamWithCRC.h b/CPP/7zip/Archive/Common/OutStreamWithCRC.h
index a034ee9b..115b442a 100755
--- a/CPP/7zip/Archive/Common/OutStreamWithCRC.h
+++ b/CPP/7zip/Archive/Common/OutStreamWithCRC.h
@@ -3,13 +3,11 @@
#ifndef __OUT_STREAM_WITH_CRC_H
#define __OUT_STREAM_WITH_CRC_H
+#include "../../../../C/7zCrc.h"
+
#include "../../../Common/MyCom.h"
-#include "../../IStream.h"
-extern "C"
-{
-#include "../../../../C/7zCrc.h"
-}
+#include "../../IStream.h"
class COutStreamWithCRC:
public ISequentialOutStream,
diff --git a/CPP/7zip/Archive/Common/OutStreamWithSha1.cpp b/CPP/7zip/Archive/Common/OutStreamWithSha1.cpp
index 51d2568a..0526c1b1 100755
--- a/CPP/7zip/Archive/Common/OutStreamWithSha1.cpp
+++ b/CPP/7zip/Archive/Common/OutStreamWithSha1.cpp
@@ -6,19 +6,13 @@
STDMETHODIMP COutStreamWithSha1::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
- UInt32 realProcessedSize;
- HRESULT result;
- if(!_stream)
- {
- realProcessedSize = size;
- result = S_OK;
- }
- else
- result = _stream->Write(data, size, &realProcessedSize);
+ HRESULT result = S_OK;
+ if (_stream)
+ result = _stream->Write(data, size, &size);
if (_calculate)
- _sha.Update((const Byte *)data, realProcessedSize);
- _size += realProcessedSize;
- if(processedSize != NULL)
- *processedSize = realProcessedSize;
+ _sha.Update((const Byte *)data, size);
+ _size += size;
+ if (processedSize != NULL)
+ *processedSize = size;
return result;
}
diff --git a/CPP/7zip/Archive/Common/OutStreamWithSha1.h b/CPP/7zip/Archive/Common/OutStreamWithSha1.h
index 4eab42a7..3bbfbbe1 100755
--- a/CPP/7zip/Archive/Common/OutStreamWithSha1.h
+++ b/CPP/7zip/Archive/Common/OutStreamWithSha1.h
@@ -3,13 +3,11 @@
#ifndef __OUT_STREAM_WITH_SHA1_H
#define __OUT_STREAM_WITH_SHA1_H
-#include "../../../Common/MyCom.h"
-#include "../../IStream.h"
-
-
-
#include "../../Crypto/Sha1.h"
+#include "../../../Common/MyCom.h"
+
+#include "../../IStream.h"
class COutStreamWithSha1:
public ISequentialOutStream,
diff --git a/CPP/7zip/Archive/Cpio/CpioHandler.cpp b/CPP/7zip/Archive/Cpio/CpioHandler.cpp
deleted file mode 100755
index d49c854f..00000000
--- a/CPP/7zip/Archive/Cpio/CpioHandler.cpp
+++ /dev/null
@@ -1,240 +0,0 @@
-// CpioHandler.cpp
-
-#include "StdAfx.h"
-
-#include "Common/ComTry.h"
-#include "Common/Defs.h"
-#include "Common/NewHandler.h"
-#include "Common/StringConvert.h"
-
-#include "Windows/PropVariant.h"
-#include "Windows/Time.h"
-
-#include "../../Common/LimitedStreams.h"
-#include "../../Common/ProgressUtils.h"
-
-#include "../../Compress/CopyCoder.h"
-
-#include "../Common/ItemNameUtils.h"
-
-#include "CpioHandler.h"
-#include "CpioIn.h"
-
-using namespace NWindows;
-using namespace NTime;
-
-namespace NArchive {
-namespace NCpio {
-
-/*
-enum
-{
- kpidinode = kpidUserDefined,
- kpidiChkSum
-};
-*/
-
-STATPROPSTG kProps[] =
-{
- { NULL, kpidPath, VT_BSTR},
- { NULL, kpidIsDir, VT_BOOL},
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
- { NULL, kpidMTime, VT_FILETIME},
- // { NULL, kpidUser, VT_BSTR},
- // { NULL, kpidGroup, VT_BSTR},
- // { L"inode", kpidinode, VT_UI4}
- // { L"CheckSum", kpidiChkSum, VT_UI4}
-};
-
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
-
-STDMETHODIMP CHandler::Open(IInStream *stream,
- const UInt64 * /* maxCheckStartPosition */,
- IArchiveOpenCallback *callback)
-{
- COM_TRY_BEGIN
- // try
- {
- CInArchive archive;
-
- UInt64 endPos = 0;
- bool needSetTotal = true;
-
- if (callback != NULL)
- {
- RINOK(stream->Seek(0, STREAM_SEEK_END, &endPos));
- RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
- }
-
- RINOK(archive.Open(stream));
-
- _items.Clear();
-
- for (;;)
- {
- CItemEx item;
- bool filled;
- HRESULT result = archive.GetNextItem(filled, item);
- if (result == S_FALSE)
- return S_FALSE;
- if (result != S_OK)
- return S_FALSE;
- if (!filled)
- break;
- _items.Add(item);
- archive.SkeepDataRecords(item.Size, item.Align);
- if (callback != NULL)
- {
- if (needSetTotal)
- {
- RINOK(callback->SetTotal(NULL, &endPos));
- needSetTotal = false;
- }
- if (_items.Size() % 100 == 0)
- {
- UInt64 numFiles = _items.Size();
- UInt64 numBytes = item.HeaderPosition;
- RINOK(callback->SetCompleted(&numFiles, &numBytes));
- }
- }
- }
- if (_items.Size() == 0)
- return S_FALSE;
-
- _inStream = stream;
- }
- /*
- catch(...)
- {
- return S_FALSE;
- }
- */
- return S_OK;
- COM_TRY_END
-}
-
-STDMETHODIMP CHandler::Close()
-{
- _items.Clear();
- _inStream.Release();
- return S_OK;
-}
-
-STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
-{
- *numItems = _items.Size();
- return S_OK;
-}
-
-STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
-{
- COM_TRY_BEGIN
- NWindows::NCOM::CPropVariant prop;
- const CItemEx &item = _items[index];
-
- switch(propID)
- {
- case kpidPath:
- prop = NItemName::GetOSName(MultiByteToUnicodeString(item.Name, CP_OEMCP));
- break;
- case kpidIsDir:
- prop = item.IsDir();
- break;
- case kpidSize:
- case kpidPackSize:
- prop = (UInt64)item.Size;
- break;
- case kpidMTime:
- {
- FILETIME utcFileTime;
- if (item.ModificationTime != 0)
- NTime::UnixTimeToFileTime(item.ModificationTime, utcFileTime);
- else
- {
- utcFileTime.dwLowDateTime = 0;
- utcFileTime.dwHighDateTime = 0;
- }
- prop = utcFileTime;
- break;
- }
- /*
- case kpidinode: prop = item.inode; break;
- case kpidiChkSum: prop = item.ChkSum; break;
- */
- }
- prop.Detach(value);
- return S_OK;
- COM_TRY_END
-}
-
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
-{
- COM_TRY_BEGIN
- bool testMode = (_aTestMode != 0);
- bool allFilesMode = (numItems == UInt32(-1));
- if (allFilesMode)
- numItems = _items.Size();
- if (numItems == 0)
- return S_OK;
- UInt64 totalSize = 0;
- UInt32 i;
- for (i = 0; i < numItems; i++)
- totalSize += _items[allFilesMode ? i : indices[i]].Size;
- extractCallback->SetTotal(totalSize);
-
- UInt64 currentTotalSize = 0;
- UInt64 currentItemSize;
-
- NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
- CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(extractCallback, false);
-
- CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
- CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_inStream);
-
- for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
- {
- lps->InSize = lps->OutSize = currentTotalSize;
- RINOK(lps->SetCur());
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode = testMode ?
- NArchive::NExtract::NAskMode::kTest :
- NArchive::NExtract::NAskMode::kExtract;
- Int32 index = allFilesMode ? i : indices[i];
- const CItemEx &item = _items[index];
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- currentItemSize = item.Size;
- if (item.IsDir())
- {
- RINOK(extractCallback->PrepareOperation(askMode));
- RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
- continue;
- }
- if (!testMode && (!realOutStream))
- continue;
- RINOK(extractCallback->PrepareOperation(askMode));
- if (testMode)
- {
- RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
- continue;
- }
- RINOK(_inStream->Seek(item.GetDataPosition(), STREAM_SEEK_SET, NULL));
- streamSpec->Init(item.Size);
- RINOK(copyCoder->Code(inStream, realOutStream, NULL, NULL, progress));
- realOutStream.Release();
- RINOK(extractCallback->SetOperationResult((copyCoderSpec->TotalSize == item.Size) ?
- NArchive::NExtract::NOperationResult::kOK:
- NArchive::NExtract::NOperationResult::kDataError));
- }
- return S_OK;
- COM_TRY_END
-}
-
-}}
diff --git a/CPP/7zip/Archive/Cpio/CpioHandler.h b/CPP/7zip/Archive/Cpio/CpioHandler.h
deleted file mode 100755
index 1993c37f..00000000
--- a/CPP/7zip/Archive/Cpio/CpioHandler.h
+++ /dev/null
@@ -1,30 +0,0 @@
-// Archive/cpio/Handler.h
-
-#ifndef __ARCHIVE_CPIO_HANDLER_H
-#define __ARCHIVE_CPIO_HANDLER_H
-
-#include "Common/MyCom.h"
-#include "../IArchive.h"
-
-#include "CpioItem.h"
-
-namespace NArchive {
-namespace NCpio {
-
-class CHandler:
- public IInArchive,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP1(IInArchive)
-
- INTERFACE_IInArchive(;)
-
-private:
- CObjectVector<CItemEx> _items;
- CMyComPtr<IInStream> _inStream;
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Cpio/CpioHeader.cpp b/CPP/7zip/Archive/Cpio/CpioHeader.cpp
deleted file mode 100755
index f7b5a414..00000000
--- a/CPP/7zip/Archive/Cpio/CpioHeader.cpp
+++ /dev/null
@@ -1,23 +0,0 @@
-// Archive/cpio/Header.h
-
-#include "StdAfx.h"
-
-#include "CpioHeader.h"
-
-namespace NArchive {
-namespace NCpio {
-namespace NFileHeader {
-
- namespace NMagic
- {
- extern const char *kMagic1 = "070701";
- extern const char *kMagic2 = "070702";
- extern const char *kMagic3 = "070707";
- extern const char *kEndName = "TRAILER!!!";
-
- const Byte kMagicForRecord2[2] = { 0xC7, 0x71 };
- // unsigned short kMagicForRecord2BE = 0xC771;
- }
-
-}}}
-
diff --git a/CPP/7zip/Archive/Cpio/CpioHeader.h b/CPP/7zip/Archive/Cpio/CpioHeader.h
deleted file mode 100755
index 21afcc17..00000000
--- a/CPP/7zip/Archive/Cpio/CpioHeader.h
+++ /dev/null
@@ -1,70 +0,0 @@
-// Archive/cpio/Header.h
-
-#ifndef __ARCHIVE_CPIO_HEADER_H
-#define __ARCHIVE_CPIO_HEADER_H
-
-#include "Common/Types.h"
-
-namespace NArchive {
-namespace NCpio {
-
-namespace NFileHeader
-{
- namespace NMagic
- {
- extern const char *kMagic1;
- extern const char *kMagic2;
- extern const char *kMagic3;
- extern const char *kEndName;
- extern const Byte kMagicForRecord2[2];
- }
-
- const UInt32 kRecord2Size = 26;
- /*
- struct CRecord2
- {
- unsigned short c_magic;
- short c_dev;
- unsigned short c_ino;
- unsigned short c_mode;
- unsigned short c_uid;
- unsigned short c_gid;
- unsigned short c_nlink;
- short c_rdev;
- unsigned short c_mtimes[2];
- unsigned short c_namesize;
- unsigned short c_filesizes[2];
- };
- */
-
- const UInt32 kRecordSize = 110;
- /*
- struct CRecord
- {
- char Magic[6]; // "070701" for "new" portable format, "070702" for CRC format
- char inode[8];
- char Mode[8];
- char UID[8];
- char GID[8];
- char nlink[8];
- char mtime[8];
- char Size[8]; // must be 0 for FIFOs and directories
- char DevMajor[8];
- char DevMinor[8];
- char RDevMajor[8]; //only valid for chr and blk special files
- char RDevMinor[8]; //only valid for chr and blk special files
- char NameSize[8]; // count includes terminating NUL in pathname
- char ChkSum[8]; // 0 for "new" portable format; for CRC format the sum of all the bytes in the file
- bool CheckMagic() const
- { return memcmp(Magic, NMagic::kMagic1, 6) == 0 ||
- memcmp(Magic, NMagic::kMagic2, 6) == 0; };
- };
- */
-
- const UInt32 kOctRecordSize = 76;
-
-}
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Cpio/CpioIn.cpp b/CPP/7zip/Archive/Cpio/CpioIn.cpp
deleted file mode 100755
index d4d807e1..00000000
--- a/CPP/7zip/Archive/Cpio/CpioIn.cpp
+++ /dev/null
@@ -1,272 +0,0 @@
-// Archive/cpioIn.cpp
-
-#include "StdAfx.h"
-
-#include "CpioIn.h"
-
-#include "Common/StringToInt.h"
-#include "Windows/Defs.h"
-
-#include "../../Common/StreamUtils.h"
-
-#include "CpioHeader.h"
-
-namespace NArchive {
-namespace NCpio {
-
-HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 &processedSize)
-{
- size_t realProcessedSize = size;
- RINOK(ReadStream(m_Stream, data, &realProcessedSize));
- processedSize = (UInt32)realProcessedSize;
- m_Position += processedSize;
- return S_OK;
-}
-
-Byte CInArchive::ReadByte()
-{
- if (_blockPos >= _blockSize)
- throw "Incorrect cpio archive";
- return _block[_blockPos++];
-}
-
-UInt16 CInArchive::ReadUInt16()
-{
- UInt16 value = 0;
- for (int i = 0; i < 2; i++)
- {
- Byte b = ReadByte();
- value |= (UInt16(b) << (8 * i));
- }
- return value;
-}
-
-UInt32 CInArchive::ReadUInt32()
-{
- UInt32 value = 0;
- for (int i = 0; i < 4; i++)
- {
- Byte b = ReadByte();
- value |= (UInt32(b) << (8 * i));
- }
- return value;
-}
-
-HRESULT CInArchive::Open(IInStream *inStream)
-{
- RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Position));
- m_Stream = inStream;
- return S_OK;
-}
-
-bool CInArchive::ReadNumber(UInt32 &resultValue)
-{
- resultValue = 0;
- for (int i = 0; i < 8; i++)
- {
- char c = char(ReadByte());
- int d;
- if (c >= '0' && c <= '9')
- d = c - '0';
- else if (c >= 'A' && c <= 'F')
- d = 10 + c - 'A';
- else if (c >= 'a' && c <= 'f')
- d = 10 + c - 'a';
- else
- return false;
- resultValue *= 0x10;
- resultValue += d;
- }
- return true;
-}
-
-static bool OctalToNumber(const char *s, UInt64 &res)
-{
- const char *end;
- res = ConvertOctStringToUInt64(s, &end);
- return (*end == ' ' || *end == 0);
-}
-
-static bool OctalToNumber32(const char *s, UInt32 &res)
-{
- UInt64 res64;
- if (!OctalToNumber(s, res64))
- return false;
- res = (UInt32)res64;
- return (res64 <= 0xFFFFFFFF);
-}
-
-bool CInArchive::ReadOctNumber(int size, UInt32 &resultValue)
-{
- char sz[32 + 4];
- int i;
- for (i = 0; i < size && i < 32; i++)
- sz[i] = (char)ReadByte();
- sz[i] = 0;
- return OctalToNumber32(sz, resultValue);
-}
-
-#define GetFromHex(y) { if (!ReadNumber(y)) return S_FALSE; }
-#define GetFromOct6(y) { if (!ReadOctNumber(6, y)) return S_FALSE; }
-#define GetFromOct11(y) { if (!ReadOctNumber(11, y)) return S_FALSE; }
-
-static unsigned short ConvertValue(unsigned short value, bool convert)
-{
- if (!convert)
- return value;
- return (unsigned short)((((unsigned short)(value & 0xFF)) << 8) | (value >> 8));
-}
-
-static UInt32 GetAlignedSize(UInt32 size, UInt32 align)
-{
- while ((size & (align - 1)) != 0)
- size++;
- return size;
-}
-
-
-HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
-{
- filled = false;
-
- UInt32 processedSize;
- item.HeaderPosition = m_Position;
-
- _blockSize = kMaxBlockSize;
- RINOK(ReadBytes(_block, 2, processedSize));
- if (processedSize != 2)
- return S_FALSE;
- _blockPos = 0;
-
- UInt32 nameSize;
-
- bool oldBE =
- _block[0] == NFileHeader::NMagic::kMagicForRecord2[1] &&
- _block[1] == NFileHeader::NMagic::kMagicForRecord2[0];
-
- bool binMode = (_block[0] == NFileHeader::NMagic::kMagicForRecord2[0] &&
- _block[1] == NFileHeader::NMagic::kMagicForRecord2[1]) ||
- oldBE;
-
- if (binMode)
- {
- RINOK(ReadBytes(_block + 2, NFileHeader::kRecord2Size - 2, processedSize));
- if (processedSize != NFileHeader::kRecord2Size - 2)
- return S_FALSE;
- item.Align = 2;
- _blockPos = 2;
- item.DevMajor = 0;
- item.DevMinor = ConvertValue(ReadUInt16(), oldBE);
- item.inode = ConvertValue(ReadUInt16(), oldBE);
- item.Mode = ConvertValue(ReadUInt16(), oldBE);
- item.UID = ConvertValue(ReadUInt16(), oldBE);
- item.GID = ConvertValue(ReadUInt16(), oldBE);
- item.NumLinks = ConvertValue(ReadUInt16(), oldBE);
- item.RDevMajor =0;
- item.RDevMinor = ConvertValue(ReadUInt16(), oldBE);
- UInt16 timeHigh = ConvertValue(ReadUInt16(), oldBE);
- UInt16 timeLow = ConvertValue(ReadUInt16(), oldBE);
- item.ModificationTime = (UInt32(timeHigh) << 16) + timeLow;
- nameSize = ConvertValue(ReadUInt16(), oldBE);
- UInt16 sizeHigh = ConvertValue(ReadUInt16(), oldBE);
- UInt16 sizeLow = ConvertValue(ReadUInt16(), oldBE);
- item.Size = (UInt32(sizeHigh) << 16) + sizeLow;
-
- item.ChkSum = 0;
- item.HeaderSize = GetAlignedSize(
- nameSize + NFileHeader::kRecord2Size, item.Align);
- nameSize = item.HeaderSize - NFileHeader::kRecord2Size;
- }
- else
- {
- RINOK(ReadBytes(_block + 2, 4, processedSize));
- if (processedSize != 4)
- return S_FALSE;
-
- bool magicOK =
- memcmp(_block, NFileHeader::NMagic::kMagic1, 6) == 0 ||
- memcmp(_block, NFileHeader::NMagic::kMagic2, 6) == 0;
- _blockPos = 6;
- if (magicOK)
- {
- RINOK(ReadBytes(_block + 6, NFileHeader::kRecordSize - 6, processedSize));
- if (processedSize != NFileHeader::kRecordSize - 6)
- return S_FALSE;
- item.Align = 4;
-
- GetFromHex(item.inode);
- GetFromHex(item.Mode);
- GetFromHex(item.UID);
- GetFromHex(item.GID);
- GetFromHex(item.NumLinks);
- UInt32 modificationTime;
- GetFromHex(modificationTime);
- item.ModificationTime = modificationTime;
- GetFromHex(item.Size);
- GetFromHex(item.DevMajor);
- GetFromHex(item.DevMinor);
- GetFromHex(item.RDevMajor);
- GetFromHex(item.RDevMinor);
- GetFromHex(nameSize);
- GetFromHex(item.ChkSum);
- item.HeaderSize = GetAlignedSize(
- nameSize + NFileHeader::kRecordSize, item.Align);
- nameSize = item.HeaderSize - NFileHeader::kRecordSize;
- }
- else
- {
- if (!memcmp(_block, NFileHeader::NMagic::kMagic3, 6) == 0)
- return S_FALSE;
- RINOK(ReadBytes(_block + 6, NFileHeader::kOctRecordSize - 6, processedSize));
- if (processedSize != NFileHeader::kOctRecordSize - 6)
- return S_FALSE;
- item.Align = 1;
- item.DevMajor = 0;
- GetFromOct6(item.DevMinor);
- GetFromOct6(item.inode);
- GetFromOct6(item.Mode);
- GetFromOct6(item.UID);
- GetFromOct6(item.GID);
- GetFromOct6(item.NumLinks);
- item.RDevMajor = 0;
- GetFromOct6(item.RDevMinor);
- UInt32 modificationTime;
- GetFromOct11(modificationTime);
- item.ModificationTime = modificationTime;
- GetFromOct6(nameSize);
- GetFromOct11(item.Size); // ?????
- item.HeaderSize = GetAlignedSize(
- nameSize + NFileHeader::kOctRecordSize, item.Align);
- nameSize = item.HeaderSize - NFileHeader::kOctRecordSize;
- }
- }
- if (nameSize == 0 || nameSize >= (1 << 27))
- return E_FAIL;
- RINOK(ReadBytes(item.Name.GetBuffer(nameSize), nameSize, processedSize));
- if (processedSize != nameSize)
- return E_FAIL;
- item.Name.ReleaseBuffer();
- if (strcmp(item.Name, NFileHeader::NMagic::kEndName) == 0)
- return S_OK;
- filled = true;
- return S_OK;
-}
-
-HRESULT CInArchive::Skeep(UInt64 numBytes)
-{
- UInt64 newPostion;
- RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));
- m_Position += numBytes;
- if (m_Position != newPostion)
- return E_FAIL;
- return S_OK;
-}
-
-HRESULT CInArchive::SkeepDataRecords(UInt64 dataSize, UInt32 align)
-{
- while ((dataSize & (align - 1)) != 0)
- dataSize++;
- return Skeep(dataSize);
-}
-
-}}
diff --git a/CPP/7zip/Archive/Cpio/CpioIn.h b/CPP/7zip/Archive/Cpio/CpioIn.h
deleted file mode 100755
index 19e3da10..00000000
--- a/CPP/7zip/Archive/Cpio/CpioIn.h
+++ /dev/null
@@ -1,41 +0,0 @@
-// CpioIn.h
-
-#ifndef __ARCHIVE_CPIO_IN_H
-#define __ARCHIVE_CPIO_IN_H
-
-#include "Common/MyCom.h"
-#include "Common/Types.h"
-#include "../../IStream.h"
-#include "CpioItem.h"
-
-namespace NArchive {
-namespace NCpio {
-
-const UInt32 kMaxBlockSize = NFileHeader::kRecordSize;
-
-class CInArchive
-{
- CMyComPtr<IInStream> m_Stream;
- UInt64 m_Position;
-
- UInt16 _blockSize;
- Byte _block[kMaxBlockSize];
- UInt32 _blockPos;
- Byte ReadByte();
- UInt16 ReadUInt16();
- UInt32 ReadUInt32();
-
- bool ReadNumber(UInt32 &resultValue);
- bool ReadOctNumber(int size, UInt32 &resultValue);
-
- HRESULT ReadBytes(void *data, UInt32 size, UInt32 &processedSize);
-public:
- HRESULT Open(IInStream *inStream);
- HRESULT GetNextItem(bool &filled, CItemEx &itemInfo);
- HRESULT Skeep(UInt64 numBytes);
- HRESULT SkeepDataRecords(UInt64 dataSize, UInt32 align);
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Cpio/CpioItem.h b/CPP/7zip/Archive/Cpio/CpioItem.h
deleted file mode 100755
index 70aa384d..00000000
--- a/CPP/7zip/Archive/Cpio/CpioItem.h
+++ /dev/null
@@ -1,55 +0,0 @@
-// Archive/cpio/ItemInfo.h
-
-#ifndef __ARCHIVE_CPIO_ITEMINFO_H
-#define __ARCHIVE_CPIO_ITEMINFO_H
-
-#include <sys/stat.h>
-
-#include "Common/Types.h"
-#include "Common/MyString.h"
-#include "CpioHeader.h"
-
-namespace NArchive {
-namespace NCpio {
-
-struct CItem
-{
- AString Name;
- UInt32 inode;
- UInt32 Mode;
- UInt32 UID;
- UInt32 GID;
- UInt32 Size;
- UInt32 ModificationTime;
-
- // char LinkFlag;
- // AString LinkName; ?????
- char Magic[8];
- UInt32 NumLinks;
- UInt32 DevMajor;
- UInt32 DevMinor;
- UInt32 RDevMajor;
- UInt32 RDevMinor;
- UInt32 ChkSum;
-
- UInt32 Align;
-
- bool IsDir() const
-#ifdef _WIN32
- { return (Mode & _S_IFMT) == _S_IFDIR; }
-#else
- { return (Mode & S_IFMT) == S_IFDIR; }
-#endif
-};
-
-class CItemEx: public CItem
-{
-public:
- UInt64 HeaderPosition;
- UInt32 HeaderSize;
- UInt64 GetDataPosition() const { return HeaderPosition + HeaderSize; };
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Cpio/CpioRegister.cpp b/CPP/7zip/Archive/Cpio/CpioRegister.cpp
deleted file mode 100755
index 62d1265e..00000000
--- a/CPP/7zip/Archive/Cpio/CpioRegister.cpp
+++ /dev/null
@@ -1,13 +0,0 @@
-// CpioRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "CpioHandler.h"
-static IInArchive *CreateArc() { return new NArchive::NCpio::CHandler; }
-
-static CArcInfo g_ArcInfo =
- { L"Cpio", L"cpio", 0, 0xED, { 0 }, 0, false, CreateArc, 0 };
-
-REGISTER_ARC(Cpio)
diff --git a/CPP/7zip/Archive/Cpio/StdAfx.h b/CPP/7zip/Archive/Cpio/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/Cpio/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/CpioHandler.cpp b/CPP/7zip/Archive/CpioHandler.cpp
new file mode 100755
index 00000000..e5a32936
--- /dev/null
+++ b/CPP/7zip/Archive/CpioHandler.cpp
@@ -0,0 +1,625 @@
+// CpioHandler.cpp
+
+#include "StdAfx.h"
+
+#include "Common/ComTry.h"
+#include "Common/StringToInt.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/PropVariant.h"
+#include "Windows/Time.h"
+
+#include "../Common/LimitedStreams.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#include "Common/ItemNameUtils.h"
+
+namespace NArchive {
+namespace NCpio {
+
+namespace NFileHeader
+{
+ namespace NMagic
+ {
+ extern const char *kMagic1 = "070701";
+ extern const char *kMagic2 = "070702";
+ extern const char *kMagic3 = "070707";
+ extern const char *kEndName = "TRAILER!!!";
+
+ const Byte kMagicForRecord2[2] = { 0xC7, 0x71 };
+ }
+
+ const UInt32 kRecord2Size = 26;
+ /*
+ struct CRecord2
+ {
+ unsigned short c_magic;
+ short c_dev;
+ unsigned short c_ino;
+ unsigned short c_mode;
+ unsigned short c_uid;
+ unsigned short c_gid;
+ unsigned short c_nlink;
+ short c_rdev;
+ unsigned short c_mtimes[2];
+ unsigned short c_namesize;
+ unsigned short c_filesizes[2];
+ };
+ */
+
+ const UInt32 kRecordSize = 110;
+ /*
+ struct CRecord
+ {
+ char Magic[6]; // "070701" for "new" portable format, "070702" for CRC format
+ char inode[8];
+ char Mode[8];
+ char UID[8];
+ char GID[8];
+ char nlink[8];
+ char mtime[8];
+ char Size[8]; // must be 0 for FIFOs and directories
+ char DevMajor[8];
+ char DevMinor[8];
+ char RDevMajor[8]; //only valid for chr and blk special files
+ char RDevMinor[8]; //only valid for chr and blk special files
+ char NameSize[8]; // count includes terminating NUL in pathname
+ char ChkSum[8]; // 0 for "new" portable format; for CRC format the sum of all the bytes in the file
+ bool CheckMagic() const
+ { return memcmp(Magic, NMagic::kMagic1, 6) == 0 ||
+ memcmp(Magic, NMagic::kMagic2, 6) == 0; };
+ };
+ */
+
+ const UInt32 kOctRecordSize = 76;
+
+}
+
+struct CItem
+{
+ AString Name;
+ UInt32 inode;
+ UInt32 Mode;
+ UInt32 UID;
+ UInt32 GID;
+ UInt32 Size;
+ UInt32 MTime;
+
+ // char LinkFlag;
+ // AString LinkName; ?????
+ char Magic[8];
+ UInt32 NumLinks;
+ UInt32 DevMajor;
+ UInt32 DevMinor;
+ UInt32 RDevMajor;
+ UInt32 RDevMinor;
+ UInt32 ChkSum;
+
+ UInt32 Align;
+
+ bool IsDir() const { return (Mode & 0170000) == 0040000; }
+};
+
+class CItemEx: public CItem
+{
+public:
+ UInt64 HeaderPosition;
+ UInt32 HeaderSize;
+ UInt64 GetDataPosition() const { return HeaderPosition + HeaderSize; };
+};
+
+const UInt32 kMaxBlockSize = NFileHeader::kRecordSize;
+
+class CInArchive
+{
+ CMyComPtr<IInStream> m_Stream;
+ UInt64 m_Position;
+
+ UInt16 _blockSize;
+ Byte _block[kMaxBlockSize];
+ UInt32 _blockPos;
+ Byte ReadByte();
+ UInt16 ReadUInt16();
+ UInt32 ReadUInt32();
+
+ bool ReadNumber(UInt32 &resultValue);
+ bool ReadOctNumber(int size, UInt32 &resultValue);
+
+ HRESULT ReadBytes(void *data, UInt32 size, UInt32 &processedSize);
+public:
+ HRESULT Open(IInStream *inStream);
+ HRESULT GetNextItem(bool &filled, CItemEx &itemInfo);
+ HRESULT Skip(UInt64 numBytes);
+ HRESULT SkipDataRecords(UInt64 dataSize, UInt32 align);
+};
+
+HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 &processedSize)
+{
+ size_t realProcessedSize = size;
+ RINOK(ReadStream(m_Stream, data, &realProcessedSize));
+ processedSize = (UInt32)realProcessedSize;
+ m_Position += processedSize;
+ return S_OK;
+}
+
+Byte CInArchive::ReadByte()
+{
+ if (_blockPos >= _blockSize)
+ throw "Incorrect cpio archive";
+ return _block[_blockPos++];
+}
+
+UInt16 CInArchive::ReadUInt16()
+{
+ UInt16 value = 0;
+ for (int i = 0; i < 2; i++)
+ {
+ Byte b = ReadByte();
+ value |= (UInt16(b) << (8 * i));
+ }
+ return value;
+}
+
+UInt32 CInArchive::ReadUInt32()
+{
+ UInt32 value = 0;
+ for (int i = 0; i < 4; i++)
+ {
+ Byte b = ReadByte();
+ value |= (UInt32(b) << (8 * i));
+ }
+ return value;
+}
+
+HRESULT CInArchive::Open(IInStream *inStream)
+{
+ RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Position));
+ m_Stream = inStream;
+ return S_OK;
+}
+
+bool CInArchive::ReadNumber(UInt32 &resultValue)
+{
+ resultValue = 0;
+ for (int i = 0; i < 8; i++)
+ {
+ char c = char(ReadByte());
+ int d;
+ if (c >= '0' && c <= '9')
+ d = c - '0';
+ else if (c >= 'A' && c <= 'F')
+ d = 10 + c - 'A';
+ else if (c >= 'a' && c <= 'f')
+ d = 10 + c - 'a';
+ else
+ return false;
+ resultValue *= 0x10;
+ resultValue += d;
+ }
+ return true;
+}
+
+static bool OctalToNumber(const char *s, UInt64 &res)
+{
+ const char *end;
+ res = ConvertOctStringToUInt64(s, &end);
+ return (*end == ' ' || *end == 0);
+}
+
+static bool OctalToNumber32(const char *s, UInt32 &res)
+{
+ UInt64 res64;
+ if (!OctalToNumber(s, res64))
+ return false;
+ res = (UInt32)res64;
+ return (res64 <= 0xFFFFFFFF);
+}
+
+bool CInArchive::ReadOctNumber(int size, UInt32 &resultValue)
+{
+ char sz[32 + 4];
+ int i;
+ for (i = 0; i < size && i < 32; i++)
+ sz[i] = (char)ReadByte();
+ sz[i] = 0;
+ return OctalToNumber32(sz, resultValue);
+}
+
+#define GetFromHex(y) { if (!ReadNumber(y)) return S_FALSE; }
+#define GetFromOct6(y) { if (!ReadOctNumber(6, y)) return S_FALSE; }
+#define GetFromOct11(y) { if (!ReadOctNumber(11, y)) return S_FALSE; }
+
+static unsigned short ConvertValue(unsigned short value, bool convert)
+{
+ if (!convert)
+ return value;
+ return (unsigned short)((((unsigned short)(value & 0xFF)) << 8) | (value >> 8));
+}
+
+static UInt32 GetAlignedSize(UInt32 size, UInt32 align)
+{
+ while ((size & (align - 1)) != 0)
+ size++;
+ return size;
+}
+
+
+HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
+{
+ filled = false;
+
+ UInt32 processedSize;
+ item.HeaderPosition = m_Position;
+
+ _blockSize = kMaxBlockSize;
+ RINOK(ReadBytes(_block, 2, processedSize));
+ if (processedSize != 2)
+ return S_FALSE;
+ _blockPos = 0;
+
+ UInt32 nameSize;
+
+ bool oldBE =
+ _block[0] == NFileHeader::NMagic::kMagicForRecord2[1] &&
+ _block[1] == NFileHeader::NMagic::kMagicForRecord2[0];
+
+ bool binMode = (_block[0] == NFileHeader::NMagic::kMagicForRecord2[0] &&
+ _block[1] == NFileHeader::NMagic::kMagicForRecord2[1]) ||
+ oldBE;
+
+ if (binMode)
+ {
+ RINOK(ReadBytes(_block + 2, NFileHeader::kRecord2Size - 2, processedSize));
+ if (processedSize != NFileHeader::kRecord2Size - 2)
+ return S_FALSE;
+ item.Align = 2;
+ _blockPos = 2;
+ item.DevMajor = 0;
+ item.DevMinor = ConvertValue(ReadUInt16(), oldBE);
+ item.inode = ConvertValue(ReadUInt16(), oldBE);
+ item.Mode = ConvertValue(ReadUInt16(), oldBE);
+ item.UID = ConvertValue(ReadUInt16(), oldBE);
+ item.GID = ConvertValue(ReadUInt16(), oldBE);
+ item.NumLinks = ConvertValue(ReadUInt16(), oldBE);
+ item.RDevMajor =0;
+ item.RDevMinor = ConvertValue(ReadUInt16(), oldBE);
+ UInt16 timeHigh = ConvertValue(ReadUInt16(), oldBE);
+ UInt16 timeLow = ConvertValue(ReadUInt16(), oldBE);
+ item.MTime = (UInt32(timeHigh) << 16) + timeLow;
+ nameSize = ConvertValue(ReadUInt16(), oldBE);
+ UInt16 sizeHigh = ConvertValue(ReadUInt16(), oldBE);
+ UInt16 sizeLow = ConvertValue(ReadUInt16(), oldBE);
+ item.Size = (UInt32(sizeHigh) << 16) + sizeLow;
+
+ item.ChkSum = 0;
+ item.HeaderSize = GetAlignedSize(
+ nameSize + NFileHeader::kRecord2Size, item.Align);
+ nameSize = item.HeaderSize - NFileHeader::kRecord2Size;
+ }
+ else
+ {
+ RINOK(ReadBytes(_block + 2, 4, processedSize));
+ if (processedSize != 4)
+ return S_FALSE;
+
+ bool magicOK =
+ memcmp(_block, NFileHeader::NMagic::kMagic1, 6) == 0 ||
+ memcmp(_block, NFileHeader::NMagic::kMagic2, 6) == 0;
+ _blockPos = 6;
+ if (magicOK)
+ {
+ RINOK(ReadBytes(_block + 6, NFileHeader::kRecordSize - 6, processedSize));
+ if (processedSize != NFileHeader::kRecordSize - 6)
+ return S_FALSE;
+ item.Align = 4;
+
+ GetFromHex(item.inode);
+ GetFromHex(item.Mode);
+ GetFromHex(item.UID);
+ GetFromHex(item.GID);
+ GetFromHex(item.NumLinks);
+ UInt32 mTime;
+ GetFromHex(mTime);
+ item.MTime = mTime;
+ GetFromHex(item.Size);
+ GetFromHex(item.DevMajor);
+ GetFromHex(item.DevMinor);
+ GetFromHex(item.RDevMajor);
+ GetFromHex(item.RDevMinor);
+ GetFromHex(nameSize);
+ GetFromHex(item.ChkSum);
+ item.HeaderSize = GetAlignedSize(
+ nameSize + NFileHeader::kRecordSize, item.Align);
+ nameSize = item.HeaderSize - NFileHeader::kRecordSize;
+ }
+ else
+ {
+ if (!memcmp(_block, NFileHeader::NMagic::kMagic3, 6) == 0)
+ return S_FALSE;
+ RINOK(ReadBytes(_block + 6, NFileHeader::kOctRecordSize - 6, processedSize));
+ if (processedSize != NFileHeader::kOctRecordSize - 6)
+ return S_FALSE;
+ item.Align = 1;
+ item.DevMajor = 0;
+ GetFromOct6(item.DevMinor);
+ GetFromOct6(item.inode);
+ GetFromOct6(item.Mode);
+ GetFromOct6(item.UID);
+ GetFromOct6(item.GID);
+ GetFromOct6(item.NumLinks);
+ item.RDevMajor = 0;
+ GetFromOct6(item.RDevMinor);
+ UInt32 mTime;
+ GetFromOct11(mTime);
+ item.MTime = mTime;
+ GetFromOct6(nameSize);
+ GetFromOct11(item.Size); // ?????
+ item.HeaderSize = GetAlignedSize(
+ nameSize + NFileHeader::kOctRecordSize, item.Align);
+ nameSize = item.HeaderSize - NFileHeader::kOctRecordSize;
+ }
+ }
+ if (nameSize == 0 || nameSize >= (1 << 27))
+ return E_FAIL;
+ RINOK(ReadBytes(item.Name.GetBuffer(nameSize), nameSize, processedSize));
+ if (processedSize != nameSize)
+ return E_FAIL;
+ item.Name.ReleaseBuffer();
+ if (strcmp(item.Name, NFileHeader::NMagic::kEndName) == 0)
+ return S_OK;
+ filled = true;
+ return S_OK;
+}
+
+HRESULT CInArchive::Skip(UInt64 numBytes)
+{
+ UInt64 newPostion;
+ RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));
+ m_Position += numBytes;
+ if (m_Position != newPostion)
+ return E_FAIL;
+ return S_OK;
+}
+
+HRESULT CInArchive::SkipDataRecords(UInt64 dataSize, UInt32 align)
+{
+ while ((dataSize & (align - 1)) != 0)
+ dataSize++;
+ return Skip(dataSize);
+}
+
+
+class CHandler:
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp
+{
+ CObjectVector<CItemEx> _items;
+ CMyComPtr<IInStream> _stream;
+public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+};
+
+/*
+enum
+{
+ kpidinode = kpidUserDefined,
+ kpidiChkSum
+};
+*/
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidIsDir, VT_BOOL},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidPosixAttrib, VT_UI4},
+ // { L"inode", kpidinode, VT_UI4}
+ // { L"CheckSum", kpidiChkSum, VT_UI4}
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_NO
+
+STDMETHODIMP CHandler::Open(IInStream *stream, const UInt64 *, IArchiveOpenCallback *callback)
+{
+ COM_TRY_BEGIN
+ // try
+ {
+ CInArchive archive;
+
+ UInt64 endPos = 0;
+ bool needSetTotal = true;
+
+ if (callback != NULL)
+ {
+ RINOK(stream->Seek(0, STREAM_SEEK_END, &endPos));
+ RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
+ }
+
+ RINOK(archive.Open(stream));
+
+ _items.Clear();
+
+ for (;;)
+ {
+ CItemEx item;
+ bool filled;
+ HRESULT result = archive.GetNextItem(filled, item);
+ if (result == S_FALSE)
+ return S_FALSE;
+ if (result != S_OK)
+ return S_FALSE;
+ if (!filled)
+ break;
+ _items.Add(item);
+ archive.SkipDataRecords(item.Size, item.Align);
+ if (callback != NULL)
+ {
+ if (needSetTotal)
+ {
+ RINOK(callback->SetTotal(NULL, &endPos));
+ needSetTotal = false;
+ }
+ if (_items.Size() % 100 == 0)
+ {
+ UInt64 numFiles = _items.Size();
+ UInt64 numBytes = item.HeaderPosition;
+ RINOK(callback->SetCompleted(&numFiles, &numBytes));
+ }
+ }
+ }
+ if (_items.Size() == 0)
+ return S_FALSE;
+
+ _stream = stream;
+ }
+ /*
+ catch(...)
+ {
+ return S_FALSE;
+ }
+ */
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _items.Clear();
+ _stream.Release();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = _items.Size();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ const CItemEx &item = _items[index];
+
+ switch(propID)
+ {
+ case kpidPath: prop = NItemName::GetOSName(MultiByteToUnicodeString(item.Name, CP_OEMCP)); break;
+ case kpidIsDir: prop = item.IsDir(); break;
+ case kpidSize:
+ case kpidPackSize:
+ prop = (UInt64)item.Size;
+ break;
+ case kpidMTime:
+ {
+ if (item.MTime != 0)
+ {
+ FILETIME utc;
+ NWindows::NTime::UnixTimeToFileTime(item.MTime, utc);
+ prop = utc;
+ }
+ break;
+ }
+ case kpidPosixAttrib: prop = item.Mode; break;
+ /*
+ case kpidinode: prop = item.inode; break;
+ case kpidiChkSum: prop = item.ChkSum; break;
+ */
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool testMode = (_aTestMode != 0);
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (allFilesMode)
+ numItems = _items.Size();
+ if (numItems == 0)
+ return S_OK;
+ UInt64 totalSize = 0;
+ UInt32 i;
+ for (i = 0; i < numItems; i++)
+ totalSize += _items[allFilesMode ? i : indices[i]].Size;
+ extractCallback->SetTotal(totalSize);
+
+ UInt64 currentTotalSize = 0;
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
+ CMyComPtr<ISequentialInStream> inStream(streamSpec);
+ streamSpec->SetStream(_stream);
+
+ for (i = 0; i < numItems; i++)
+ {
+ lps->InSize = lps->OutSize = currentTotalSize;
+ RINOK(lps->SetCur());
+ CMyComPtr<ISequentialOutStream> outStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ Int32 index = allFilesMode ? i : indices[i];
+ const CItemEx &item = _items[index];
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
+ currentTotalSize += item.Size;
+ if (item.IsDir())
+ {
+ RINOK(extractCallback->PrepareOperation(askMode));
+ RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
+ continue;
+ }
+ if (!testMode && !outStream)
+ continue;
+ RINOK(extractCallback->PrepareOperation(askMode));
+ if (testMode)
+ {
+ RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
+ continue;
+ }
+ RINOK(_stream->Seek(item.GetDataPosition(), STREAM_SEEK_SET, NULL));
+ streamSpec->Init(item.Size);
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ outStream.Release();
+ RINOK(extractCallback->SetOperationResult((copyCoderSpec->TotalSize == item.Size) ?
+ NArchive::NExtract::NOperationResult::kOK:
+ NArchive::NExtract::NOperationResult::kDataError));
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ const CItemEx &item = _items[index];
+ return CreateLimitedInStream(_stream, item.GetDataPosition(), item.Size, stream);
+ COM_TRY_END
+}
+
+static IInArchive *CreateArc() { return new NArchive::NCpio::CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"Cpio", L"cpio", 0, 0xED, { 0 }, 0, false, CreateArc, 0 };
+
+REGISTER_ARC(Cpio)
+
+}}
diff --git a/CPP/7zip/Archive/DebHandler.cpp b/CPP/7zip/Archive/DebHandler.cpp
index fc962df3..0381e0fd 100755
--- a/CPP/7zip/Archive/DebHandler.cpp
+++ b/CPP/7zip/Archive/DebHandler.cpp
@@ -30,7 +30,7 @@ namespace NHeader
{
const int kSignatureLen = 8;
- const char *kSignature = "!<arch>\n";
+ const char *kSignature = "!<arch>\n";
const int kNameSize = 16;
const int kTimeSize = 12;
@@ -53,20 +53,15 @@ namespace NHeader
const int kHeaderSize = kNameSize + kTimeSize + 6 + 6 + kModeSize + kSizeSize + 1 + 1;
}
-class CItem
+struct CItem
{
-public:
AString Name;
UInt64 Size;
UInt32 MTime;
UInt32 Mode;
-};
-class CItemEx: public CItem
-{
-public:
- UInt64 HeaderPosition;
- UInt64 GetDataPosition() const { return HeaderPosition + NHeader::kHeaderSize; };
+ UInt64 HeaderPos;
+ UInt64 GetDataPos() const { return HeaderPos + NHeader::kHeaderSize; };
// UInt64 GetFullSize() const { return NFileHeader::kRecordSize + Size; };
};
@@ -75,12 +70,11 @@ class CInArchive
CMyComPtr<IInStream> m_Stream;
UInt64 m_Position;
- HRESULT GetNextItemReal(bool &filled, CItemEx &itemInfo);
- HRESULT Skeep(UInt64 numBytes);
+ HRESULT GetNextItemReal(bool &filled, CItem &itemInfo);
public:
HRESULT Open(IInStream *inStream);
- HRESULT GetNextItem(bool &filled, CItemEx &itemInfo);
- HRESULT SkeepData(UInt64 dataSize);
+ HRESULT GetNextItem(bool &filled, CItem &itemInfo);
+ HRESULT SkipData(UInt64 dataSize);
};
HRESULT CInArchive::Open(IInStream *inStream)
@@ -151,7 +145,7 @@ static bool DecimalToNumber32(const char *s, int size, UInt32 &res)
#define RIF(x) { if (!(x)) return S_FALSE; }
-HRESULT CInArchive::GetNextItemReal(bool &filled, CItemEx &item)
+HRESULT CInArchive::GetNextItemReal(bool &filled, CItem &item)
{
filled = false;
@@ -159,7 +153,7 @@ HRESULT CInArchive::GetNextItemReal(bool &filled, CItemEx &item)
const char *cur = header;
size_t processedSize = sizeof(header);
- item.HeaderPosition = m_Position;
+ item.HeaderPos = m_Position;
RINOK(ReadStream(m_Stream, header, &processedSize));
m_Position += processedSize;
if (processedSize != sizeof(header))
@@ -191,7 +185,7 @@ HRESULT CInArchive::GetNextItemReal(bool &filled, CItemEx &item)
return S_OK;
}
-HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
+HRESULT CInArchive::GetNextItem(bool &filled, CItem &item)
{
for (;;)
{
@@ -202,38 +196,26 @@ HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
return S_OK;
if (item.Size != 4)
return S_OK;
- SkeepData(item.Size);
+ SkipData(item.Size);
}
}
-HRESULT CInArchive::Skeep(UInt64 numBytes)
+HRESULT CInArchive::SkipData(UInt64 dataSize)
{
- UInt64 newPostion;
- RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));
- m_Position += numBytes;
- if (m_Position != newPostion)
- return E_FAIL;
- return S_OK;
+ return m_Stream->Seek((dataSize + 1) & (~((UInt64)0x1)), STREAM_SEEK_CUR, &m_Position);
}
-HRESULT CInArchive::SkeepData(UInt64 dataSize)
-{
- return Skeep((dataSize + 1) & (~((UInt64)0x1)));
-}
-
-
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
+ CObjectVector<CItem> _items;
+ CMyComPtr<IInStream> _stream;
public:
- MY_UNKNOWN_IMP1(IInArchive)
-
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
INTERFACE_IInArchive(;)
-
-private:
- CObjectVector<CItemEx> _items;
- CMyComPtr<IInStream> _inStream;
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
@@ -241,7 +223,6 @@ STATPROPSTG kProps[] =
{
{ NULL, kpidPath, VT_BSTR},
{ NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
{ NULL, kpidMTime, VT_FILETIME}
};
@@ -268,7 +249,7 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
for (;;)
{
- CItemEx item;
+ CItem item;
bool filled;
HRESULT result = archive.GetNextItem(filled, item);
if (result == S_FALSE)
@@ -278,14 +259,14 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
if (!filled)
break;
_items.Add(item);
- archive.SkeepData(item.Size);
+ archive.SkipData(item.Size);
if (openArchiveCallback != NULL)
{
UInt64 numFiles = _items.Size();
RINOK(openArchiveCallback->SetCompleted(&numFiles, NULL));
}
}
- _inStream = stream;
+ _stream = stream;
}
return S_OK;
COM_TRY_END
@@ -293,7 +274,7 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
STDMETHODIMP CHandler::Close()
{
- _inStream.Release();
+ _stream.Release();
_items.Clear();
return S_OK;
}
@@ -308,7 +289,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
{
COM_TRY_BEGIN
NWindows::NCOM::CPropVariant prop;
- const CItemEx &item = _items[index];
+ const CItem &item = _items[index];
switch(propID)
{
@@ -350,7 +331,6 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
extractCallback->SetTotal(totalSize);
UInt64 currentTotalSize = 0;
- UInt64 currentItemSize;
NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
@@ -361,9 +341,9 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_inStream);
+ streamSpec->SetStream(_stream);
- for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
+ for (i = 0; i < numItems; i++)
{
lps->InSize = lps->OutSize = currentTotalSize;
RINOK(lps->SetCur());
@@ -372,14 +352,9 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
NArchive::NExtract::NAskMode::kTest :
NArchive::NExtract::NAskMode::kExtract;
Int32 index = allFilesMode ? i : indices[i];
- const CItemEx &item = _items[index];
+ const CItem &item = _items[index];
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- currentItemSize = item.Size;
-
-
-
-
-
+ currentTotalSize += item.Size;
if (!testMode && (!realOutStream))
continue;
@@ -389,7 +364,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
continue;
}
- RINOK(_inStream->Seek(item.GetDataPosition(), STREAM_SEEK_SET, NULL));
+ RINOK(_stream->Seek(item.GetDataPos(), STREAM_SEEK_SET, NULL));
streamSpec->Init(item.Size);
RINOK(copyCoder->Code(inStream, realOutStream, NULL, NULL, progress));
realOutStream.Release();
@@ -401,10 +376,18 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
COM_TRY_END
}
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ const CItem &item = _items[index];
+ return CreateLimitedInStream(_stream, item.GetDataPos(), item.Size, stream);
+ COM_TRY_END
+}
+
static IInArchive *CreateArc() { return new NArchive::NDeb::CHandler; }
static CArcInfo g_ArcInfo =
- { L"Deb", L"deb", 0, 0xEC, { '!', '<', 'a', 'r', 'c', 'h', '>', '\n' }, 8, false, CreateArc, 0 };
+ { L"Deb", L"deb", 0, 0xEC, { '!', '<', 'a', 'r', 'c', 'h', '>', '\n' }, 8, false, CreateArc, 0 };
REGISTER_ARC(Deb)
diff --git a/CPP/7zip/Archive/DllExports2.cpp b/CPP/7zip/Archive/DllExports2.cpp
index 545fcbd3..fd8bff28 100755
--- a/CPP/7zip/Archive/DllExports2.cpp
+++ b/CPP/7zip/Archive/DllExports2.cpp
@@ -7,10 +7,7 @@
#include "../../Common/Types.h"
#include "../../Windows/PropVariant.h"
#if defined(_WIN32) && defined(_7ZIP_LARGE_PAGES)
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#endif
#include "IArchive.h"
diff --git a/CPP/7zip/Archive/ElfHandler.cpp b/CPP/7zip/Archive/ElfHandler.cpp
index cac7c3ad..66b18e7a 100755
--- a/CPP/7zip/Archive/ElfHandler.cpp
+++ b/CPP/7zip/Archive/ElfHandler.cpp
@@ -17,8 +17,6 @@
#include "../Compress/CopyCoder.h"
-#include "Common/DummyOutStream.h"
-
static UInt16 Get16(const Byte *p, int be) { if (be) return GetBe16(p); return GetUi16(p); }
static UInt32 Get32(const Byte *p, int be) { if (be) return GetBe32(p); return GetUi32(p); }
static UInt64 Get64(const Byte *p, int be) { if (be) return GetBe64(p); return GetUi64(p); }
@@ -28,11 +26,11 @@ using namespace NWindows;
namespace NArchive {
namespace NElf {
-#define ELF_CLASS_32 1
-#define ELF_CLASS_64 2
+#define ELF_CLASS_32 1
+#define ELF_CLASS_64 2
-#define ELF_DATA_2LSB 1
-#define ELF_DATA_2MSB 2
+#define ELF_DATA_2LSB 1
+#define ELF_DATA_2MSB 2
#define NUM_SCAN_SECTIONS_MAX (1 << 6)
@@ -321,7 +319,7 @@ public:
INTERFACE_IInArchive(;)
};
-#define ELF_PT_PHDR 6
+#define ELF_PT_PHDR 6
bool CHandler::Parse(const Byte *buf, UInt32 size)
{
@@ -498,9 +496,6 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CMyComPtr<ISequentialInStream> inStream(streamSpec);
streamSpec->SetStream(_inStream);
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
-
for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
{
lps->InSize = lps->OutSize = currentTotalSize;
@@ -511,20 +506,17 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
UInt32 index = allFilesMode ? i : indices[i];
const CSegment &item = _sections[index];
currentItemSize = item.PSize;
- {
- CMyComPtr<ISequentialOutStream> realOutStream;
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- if (!testMode && (!realOutStream))
- continue;
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
- }
+
+ CMyComPtr<ISequentialOutStream> outStream;
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
+ if (!testMode && !outStream)
+ continue;
RINOK(extractCallback->PrepareOperation(askMode));
RINOK(_inStream->Seek(item.Offset, STREAM_SEEK_SET, NULL));
streamSpec->Init(currentItemSize);
RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
- outStreamSpec->ReleaseStream();
+ outStream.Release();
RINOK(extractCallback->SetOperationResult(copyCoderSpec->TotalSize == currentItemSize ?
NArchive::NExtract::NOperationResult::kOK:
NArchive::NExtract::NOperationResult::kDataError));
diff --git a/CPP/7zip/Archive/FatHandler.cpp b/CPP/7zip/Archive/FatHandler.cpp
new file mode 100755
index 00000000..f07d4ccb
--- /dev/null
+++ b/CPP/7zip/Archive/FatHandler.cpp
@@ -0,0 +1,983 @@
+// FatHandler.cpp
+
+#include "StdAfx.h"
+
+// #include <stdio.h>
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/Buffer.h"
+#include "Common/ComTry.h"
+#include "Common/IntToString.h"
+#include "Common/MyCom.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/PropVariant.h"
+#include "Windows/Time.h"
+
+#include "../Common/LimitedStreams.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#include "Common/DummyOutStream.h"
+
+#define Get16(p) GetUi16(p)
+#define Get32(p) GetUi32(p)
+
+#define PRF(x) /* x */
+
+namespace NArchive {
+namespace NFat {
+
+static const UInt32 kFatItemUsedByDirMask = (UInt32)1 << 31;
+
+struct CHeader
+{
+ UInt32 NumSectors;
+ UInt16 NumReservedSectors;
+ Byte NumFats;
+ UInt32 NumFatSectors;
+ UInt32 RootDirSector;
+ UInt32 NumRootDirSectors;
+ UInt32 DataSector;
+
+ UInt32 FatSize;
+ UInt32 BadCluster;
+
+ Byte NumFatBits;
+ Byte SectorSizeLog;
+ Byte SectorsPerClusterLog;
+ Byte ClusterSizeLog;
+
+ UInt16 SectorsPerTrack;
+ UInt16 NumHeads;
+ UInt32 NumHiddenSectors;
+
+ bool VolFieldsDefined;
+
+ UInt32 VolId;
+ // Byte VolName[11];
+ // Byte FileSys[8];
+
+ // Byte OemName[5];
+ Byte MediaType;
+
+ // 32-bit FAT
+ UInt16 Flags;
+ UInt16 FsInfoSector;
+ UInt32 RootCluster;
+
+ bool IsFat32() const { return NumFatBits == 32; }
+ UInt64 GetPhySize() const { return (UInt64)NumSectors << SectorSizeLog; }
+ UInt32 SectorSize() const { return (UInt32)1 << SectorSizeLog; }
+ UInt32 ClusterSize() const { return (UInt32)1 << ClusterSizeLog; }
+ UInt32 ClusterToSector(UInt32 c) const { return DataSector + ((c - 2) << SectorsPerClusterLog); }
+ UInt32 IsEoc(UInt32 c) const { return c > BadCluster; }
+ UInt32 IsEocAndUnused(UInt32 c) const { return c > BadCluster && (c & kFatItemUsedByDirMask) == 0; }
+ UInt32 IsValidCluster(UInt32 c) const { return c >= 2 && c < FatSize; }
+ UInt32 SizeToSectors(UInt32 size) const { return (size + SectorSize() - 1) >> SectorSizeLog; }
+ UInt32 CalcFatSizeInSectors() const { return SizeToSectors((FatSize * (NumFatBits / 4) + 1) / 2); }
+
+ UInt32 GetFatSector() const
+ {
+ UInt32 index = (IsFat32() && (Flags & 0x80) != 0) ? (Flags & 0xF) : 0;
+ if (index > NumFats)
+ index = 0;
+ return NumReservedSectors + index * NumFatSectors;
+ }
+
+ UInt64 GetFilePackSize(UInt32 unpackSize) const
+ {
+ UInt64 mask = ClusterSize() - 1;
+ return (unpackSize + mask) & ~mask;
+ }
+
+ UInt32 GetNumClusters(UInt32 size) const
+ { return (UInt32)(((UInt64)size + ClusterSize() - 1) >> ClusterSizeLog); }
+
+ bool Parse(const Byte *p);
+};
+
+static int GetLog(UInt32 num)
+{
+ for (int i = 0; i < 31; i++)
+ if (((UInt32)1 << i) == num)
+ return i;
+ return -1;
+}
+
+bool CHeader::Parse(const Byte *p)
+{
+ if (p[0x1FE] != 0x55 || p[0x1FF] != 0xAA)
+ return false;
+
+ int codeOffset = 0;
+ switch (p[0])
+ {
+ case 0xE9: codeOffset = 3 + (Int16)Get16(p + 1); break;
+ case 0xEB: if (p[2] != 0x90) return false; codeOffset = 2 + (signed char)p[1]; break;
+ default: return false;
+ }
+ {
+ int s = GetLog(Get16(p + 11));
+ if (s < 9 || s > 12)
+ return false;
+ SectorSizeLog = (Byte)s;
+ s = GetLog(p[13]);
+ if (s < 0)
+ return false;
+ SectorsPerClusterLog = (Byte)s;
+ ClusterSizeLog = SectorSizeLog + SectorsPerClusterLog;
+ }
+
+ NumReservedSectors = Get16(p + 14);
+ if (NumReservedSectors == 0)
+ return false;
+
+ NumFats = p[16];
+ if (NumFats < 1 || NumFats > 4)
+ return false;
+
+ UInt16 numRootDirEntries = Get16(p + 17);
+ if (numRootDirEntries == 0)
+ {
+ if (codeOffset < 90)
+ return false;
+ NumFatBits = 32;
+ NumRootDirSectors = 0;
+ }
+ else
+ {
+ if (codeOffset < 62)
+ return false;
+ NumFatBits = 0;
+ UInt32 mask = (1 << (SectorSizeLog - 5)) - 1;
+ if ((numRootDirEntries & mask) != 0)
+ return false;
+ NumRootDirSectors = (numRootDirEntries + mask) >> (SectorSizeLog - 5);
+ }
+
+ NumSectors = Get16(p + 19);
+ if (NumSectors == 0)
+ NumSectors = Get32(p + 32);
+ else if (IsFat32())
+ return false;
+
+ MediaType = p[21];
+ NumFatSectors = Get16(p + 22);
+ SectorsPerTrack = Get16(p + 24);
+ NumHeads = Get16(p + 26);
+ NumHiddenSectors = Get32(p + 28);
+
+ // memcpy(OemName, p + 3, 5);
+
+ p += 36;
+ if (IsFat32())
+ {
+ if (NumFatSectors != 0)
+ return false;
+ NumFatSectors = Get32(p);
+ if (NumFatSectors >= (1 << 24))
+ return false;
+
+ Flags = Get16(p + 4);
+ if (Get16(p + 6) != 0)
+ return false;
+ RootCluster = Get32(p + 8);
+ FsInfoSector = Get16(p + 12);
+ for (int i = 16; i < 28; i++)
+ if (p[i] != 0)
+ return false;
+ p += 28;
+ }
+
+ // DriveNumber = p[0];
+ VolFieldsDefined = (p[2] == 0x29); // ExtendedBootSig
+ VolId = Get32(p + 3);
+ // memcpy(VolName, p + 7, 11);
+ // memcpy(FileSys, p + 18, 8);
+
+ if (NumFatSectors == 0)
+ return false;
+ RootDirSector = NumReservedSectors + NumFatSectors * NumFats;
+ DataSector = RootDirSector + NumRootDirSectors;
+ if (NumSectors < DataSector)
+ return false;
+ UInt32 numDataSectors = NumSectors - DataSector;
+ UInt32 numClusters = numDataSectors >> SectorsPerClusterLog;
+
+ BadCluster = 0x0FFFFFF7;
+ if (numClusters < 0xFFF5)
+ {
+ if (NumFatBits == 32)
+ return false;
+ NumFatBits = (numClusters < 0xFF5) ? 12: 16;
+ BadCluster &= ((1 << NumFatBits) - 1);
+ }
+ else if (NumFatBits != 32)
+ return false;
+
+ FatSize = numClusters + 2;
+ if (FatSize > BadCluster || CalcFatSizeInSectors() > NumFatSectors)
+ return false;
+ return true;
+}
+
+struct CItem
+{
+ UString UName;
+ char DosName[11];
+ Byte CTime2;
+ UInt32 CTime;
+ UInt32 MTime;
+ UInt16 ADate;
+ Byte Attrib;
+ Byte Flags;
+ UInt32 Size;
+ UInt32 Cluster;
+ Int32 Parent;
+
+ // NT uses Flags to store Low Case status
+ bool NameIsLow() const { return (Flags & 0x8) != 0; }
+ bool ExtIsLow() const { return (Flags & 0x10) != 0; }
+ bool IsDir() const { return (Attrib & 0x10) != 0; }
+ UString GetShortName() const;
+ UString GetName() const;
+ UString GetVolName() const;
+};
+
+static int CopyAndTrim(char *dest, const char *src, int size, bool toLower)
+{
+ int i;
+ memcpy(dest, src, size);
+ if (toLower)
+ for (i = 0; i < size; i++)
+ {
+ char c = dest[i];
+ if (c >= 'A' && c <= 'Z')
+ dest[i] = c + 0x20;
+ }
+ for (i = size - 1; i >= 0 && dest[i] == ' '; i--);
+ return i + 1;
+}
+
+static UString FatStringToUnicode(const char *s)
+{
+ return MultiByteToUnicodeString(s, CP_OEMCP);
+}
+
+UString CItem::GetShortName() const
+{
+ char s[16];
+ int i = CopyAndTrim(s, DosName, 8, NameIsLow());
+ s[i++] = '.';
+ int j = CopyAndTrim(s + i, DosName + 8, 3, ExtIsLow());
+ if (j == 0)
+ j--;
+ s[i + j] = 0;
+ return FatStringToUnicode(s);
+}
+
+UString CItem::GetName() const
+{
+ if (!UName.IsEmpty())
+ return UName;
+ return GetShortName();
+}
+
+UString CItem::GetVolName() const
+{
+ if (!UName.IsEmpty())
+ return UName;
+ char s[12];
+ int i = CopyAndTrim(s, DosName, 11, false);
+ s[i] = 0;
+ return FatStringToUnicode(s);
+}
+
+struct CDatabase
+{
+ CHeader Header;
+ CObjectVector<CItem> Items;
+ UInt32 *Fat;
+ CMyComPtr<IInStream> InStream;
+ IArchiveOpenCallback *OpenCallback;
+
+ UInt32 NumFreeClusters;
+ bool VolItemDefined;
+ CItem VolItem;
+ UInt32 NumDirClusters;
+ CByteBuffer ByteBuf;
+ UInt64 NumCurUsedBytes;
+
+ CDatabase(): Fat(0) {}
+ ~CDatabase() { ClearAndClose(); }
+
+ void Clear();
+ void ClearAndClose();
+ HRESULT OpenProgressFat(bool changeTotal = true);
+ HRESULT OpenProgress();
+
+ UString GetItemPath(Int32 index) const;
+ HRESULT Open();
+ HRESULT ReadDir(Int32 parent, UInt32 cluster, int level);
+
+ UInt64 GetHeadersSize() const
+ {
+ return (UInt64)(Header.DataSector + (NumDirClusters << Header.SectorsPerClusterLog)) << Header.SectorSizeLog;
+ }
+ HRESULT SeekToSector(UInt32 sector);
+ HRESULT SeekToCluster(UInt32 cluster) { return SeekToSector(Header.ClusterToSector(cluster)); }
+};
+
+HRESULT CDatabase::SeekToSector(UInt32 sector)
+{
+ return InStream->Seek((UInt64)sector << Header.SectorSizeLog, STREAM_SEEK_SET, NULL);
+}
+
+void CDatabase::Clear()
+{
+ VolItemDefined = false;
+ NumDirClusters = 0;
+ NumCurUsedBytes = 0;
+
+ Items.Clear();
+ delete []Fat;
+ Fat = 0;
+}
+
+void CDatabase::ClearAndClose()
+{
+ Clear();
+ InStream.Release();
+}
+
+HRESULT CDatabase::OpenProgressFat(bool changeTotal)
+{
+ if (!OpenCallback)
+ return S_OK;
+ if (changeTotal)
+ {
+ UInt64 numTotalBytes = (Header.CalcFatSizeInSectors() << Header.SectorSizeLog) +
+ ((UInt64)(Header.FatSize - NumFreeClusters) << Header.ClusterSizeLog);
+ RINOK(OpenCallback->SetTotal(NULL, &numTotalBytes));
+ }
+ return OpenCallback->SetCompleted(NULL, &NumCurUsedBytes);
+}
+
+HRESULT CDatabase::OpenProgress()
+{
+ if (!OpenCallback)
+ return S_OK;
+ UInt64 numItems = Items.Size();
+ return OpenCallback->SetCompleted(&numItems, &NumCurUsedBytes);
+}
+
+UString CDatabase::GetItemPath(Int32 index) const
+{
+ const CItem *item = &Items[index];
+ UString name = item->GetName();
+ for (;;)
+ {
+ index = item->Parent;
+ if (index < 0)
+ return name;
+ item = &Items[index];
+ name = item->GetName() + WCHAR_PATH_SEPARATOR + name;
+ }
+}
+
+static wchar_t *AddSubStringToName(wchar_t *dest, const Byte *p, int numChars)
+{
+ for (int i = 0; i < numChars; i++)
+ {
+ wchar_t c = Get16(p + i * 2);
+ if (c != 0 && c != 0xFFFF)
+ *dest++ = c;
+ }
+ *dest = 0;
+ return dest;
+}
+
+HRESULT CDatabase::ReadDir(Int32 parent, UInt32 cluster, int level)
+{
+ int startIndex = Items.Size();
+ if (startIndex >= (1 << 30) || level > 256)
+ return S_FALSE;
+
+ UInt32 sectorIndex = 0;
+ UInt32 blockSize = Header.ClusterSize();
+ bool clusterMode = (Header.IsFat32() || parent >= 0);
+ if (!clusterMode)
+ {
+ blockSize = Header.SectorSize();
+ RINOK(SeekToSector(Header.RootDirSector));
+ }
+
+ ByteBuf.SetCapacity(blockSize);
+ UString curName;
+ int checkSum = -1;
+ int numLongRecords = -1;
+ for (UInt32 pos = blockSize;; pos += 32)
+ {
+ if (pos == blockSize)
+ {
+ pos = 0;
+
+ if ((NumDirClusters & 0xFF) == 0)
+ {
+ RINOK(OpenProgress());
+ }
+
+ if (clusterMode)
+ {
+ if (Header.IsEoc(cluster))
+ break;
+ if (!Header.IsValidCluster(cluster))
+ return S_FALSE;
+ PRF(printf("\nCluster = %4X", cluster));
+ RINOK(SeekToCluster(cluster));
+ UInt32 newCluster = Fat[cluster];
+ if ((newCluster & kFatItemUsedByDirMask) != 0)
+ return S_FALSE;
+ Fat[cluster] |= kFatItemUsedByDirMask;
+ cluster = newCluster;
+ NumDirClusters++;
+ NumCurUsedBytes += Header.ClusterSize();
+ }
+ else if (sectorIndex++ >= Header.NumRootDirSectors)
+ break;
+
+ RINOK(ReadStream_FALSE(InStream, ByteBuf, blockSize));
+ }
+ const Byte *p = ByteBuf + pos;
+ if (p[0] == 0)
+ {
+ if (clusterMode && !Header.IsEoc(cluster))
+ return S_FALSE;
+ break;
+ }
+ if (p[0] == 0xE5)
+ {
+ if (numLongRecords > 0)
+ return S_FALSE;
+ continue;
+ }
+
+ Byte attrib = p[11];
+ if ((attrib & 0x3F) == 0xF)
+ {
+ if (p[0] > 0x7F || Get16(p + 26) != 0)
+ return S_FALSE;
+ int longIndex = p[0] & 0x3F;
+ if (longIndex == 0)
+ return S_FALSE;
+ bool isLast = (p[0] & 0x40) != 0;
+ if (numLongRecords < 0)
+ {
+ if (!isLast)
+ return S_FALSE;
+ numLongRecords = longIndex;
+ }
+ else if (isLast || numLongRecords != longIndex)
+ return S_FALSE;
+
+ numLongRecords--;
+
+ if (p[12] == 0)
+ {
+ wchar_t nameBuf[14];
+ wchar_t *dest;
+
+ dest = AddSubStringToName(nameBuf, p + 1, 5);
+ dest = AddSubStringToName(dest, p + 14, 6);
+ AddSubStringToName(dest, p + 28, 2);
+ curName = nameBuf + curName;
+ if (isLast)
+ checkSum = p[13];
+ if (checkSum != p[13])
+ return S_FALSE;
+ }
+ }
+ else
+ {
+ if (numLongRecords > 0)
+ return S_FALSE;
+ CItem item;
+ memcpy(item.DosName, p, 11);
+
+ if (checkSum >= 0)
+ {
+ Byte sum = 0;
+ for (int i = 0; i < 11; i++)
+ sum = ((sum & 1) ? 0x80 : 0) + (sum >> 1) + (Byte)item.DosName[i];
+ if (sum == checkSum)
+ item.UName = curName;
+ }
+
+ if (item.DosName[0] == 5)
+ item.DosName[0] = (char)(Byte)0xE5;
+ item.Attrib = attrib;
+ item.Flags = p[12];
+ item.Size = Get32(p + 28);
+ item.Cluster = Get16(p + 26) | ((UInt32)Get16(p + 20) << 16);
+ item.CTime = Get32(p + 14);
+ item.CTime2 = p[13];
+ item.ADate = Get16(p + 18);
+ item.MTime = Get32(p + 22);
+ item.Parent = parent;
+
+ if (attrib == 8)
+ {
+ VolItem = item;
+ VolItemDefined = true;
+ }
+ else
+ if (memcmp(item.DosName, ". ", 11) != 0 &&
+ memcmp(item.DosName, ".. ", 11) != 0)
+ {
+ if (!item.IsDir())
+ NumCurUsedBytes += Header.GetFilePackSize(item.Size);
+ Items.Add(item);
+ PRF(printf("\n%7d: %S", Items.Size(), GetItemPath(Items.Size() - 1)));
+ }
+ numLongRecords = -1;
+ curName.Empty();
+ checkSum = -1;
+ }
+ }
+
+ int finishIndex = Items.Size();
+ for (int i = startIndex; i < finishIndex; i++)
+ {
+ const CItem &item = Items[i];
+ if (item.IsDir())
+ {
+ PRF(printf("\n%S", GetItemPath(i)));
+ RINOK(CDatabase::ReadDir(i, item.Cluster, level + 1));
+ }
+ }
+ return S_OK;
+}
+
+HRESULT CDatabase::Open()
+{
+ Clear();
+ bool numFreeClustersDefined = false;
+ {
+ static const UInt32 kHeaderSize = 512;
+ Byte buf[kHeaderSize];
+ RINOK(ReadStream_FALSE(InStream, buf, kHeaderSize));
+ if (!Header.Parse(buf))
+ return S_FALSE;
+ UInt64 fileSize;
+ RINOK(InStream->Seek(0, STREAM_SEEK_END, &fileSize));
+ if (fileSize < Header.GetPhySize())
+ return S_FALSE;
+
+ if (Header.IsFat32())
+ {
+ SeekToSector(Header.FsInfoSector);
+ RINOK(ReadStream_FALSE(InStream, buf, kHeaderSize));
+ if (buf[0x1FE] != 0x55 || buf[0x1FF] != 0xAA)
+ return S_FALSE;
+ if (Get32(buf) == 0x41615252 && Get32(buf + 484) == 0x61417272)
+ {
+ NumFreeClusters = Get32(buf + 488);
+ numFreeClustersDefined = (NumFreeClusters <= Header.FatSize);
+ }
+ }
+ }
+
+ // numFreeClustersDefined = false; // to recalculate NumFreeClusters
+ if (!numFreeClustersDefined)
+ NumFreeClusters = 0;
+
+ CByteBuffer byteBuf;
+ Fat = new UInt32[Header.FatSize];
+
+ RINOK(OpenProgressFat());
+ RINOK(SeekToSector(Header.GetFatSector()));
+ if (Header.NumFatBits == 32)
+ {
+ const UInt32 kBufSize = (1 << 15);
+ byteBuf.SetCapacity(kBufSize);
+ for (UInt32 i = 0; i < Header.FatSize;)
+ {
+ UInt32 size = Header.FatSize - i;
+ const UInt32 kBufSize32 = kBufSize / 4;
+ if (size > kBufSize32)
+ size = kBufSize32;
+ UInt32 readSize = Header.SizeToSectors(size * 4) << Header.SectorSizeLog;
+ RINOK(ReadStream_FALSE(InStream, byteBuf, readSize));
+ NumCurUsedBytes += readSize;
+
+ const UInt32 *src = (const UInt32 *)(const Byte *)byteBuf;
+ UInt32 *dest = Fat + i;
+ if (numFreeClustersDefined)
+ for (UInt32 j = 0; j < size; j++)
+ dest[j] = Get32(src + j) & 0x0FFFFFFF;
+ else
+ {
+ UInt32 numFreeClusters = 0;
+ for (UInt32 j = 0; j < size; j++)
+ {
+ UInt32 v = Get32(src + j) & 0x0FFFFFFF;
+ numFreeClusters += (UInt32)(v - 1) >> 31;
+ dest[j] = v;
+ }
+ NumFreeClusters += numFreeClusters;
+ }
+ i += size;
+ if ((i & 0xFFFFF) == 0)
+ {
+ RINOK(OpenProgressFat(!numFreeClustersDefined));
+ }
+ }
+ }
+ else
+ {
+ const UInt32 kBufSize = (UInt32)Header.CalcFatSizeInSectors() << Header.SectorSizeLog;
+ NumCurUsedBytes += kBufSize;
+ byteBuf.SetCapacity(kBufSize);
+ Byte *p = byteBuf;
+ RINOK(ReadStream_FALSE(InStream, p, kBufSize));
+ UInt32 fatSize = Header.FatSize;
+ UInt32 *fat = &Fat[0];
+ if (Header.NumFatBits == 16)
+ for (UInt32 j = 0; j < fatSize; j++)
+ fat[j] = Get16(p + j * 2);
+ else
+ for (UInt32 j = 0; j < fatSize; j++)
+ fat[j] = (Get16(p + j * 3 / 2) >> ((j & 1) << 2)) & 0xFFF;
+
+ if (!numFreeClustersDefined)
+ {
+ UInt32 numFreeClusters = 0;
+ for (UInt32 i = 0; i < fatSize; i++)
+ numFreeClusters += (UInt32)(fat[i] - 1) >> 31;
+ NumFreeClusters = numFreeClusters;
+ }
+ }
+
+ RINOK(OpenProgressFat());
+
+ if ((Fat[0] & 0xFF) != Header.MediaType)
+ return S_FALSE;
+
+ return ReadDir(-1, Header.RootCluster, 0);
+}
+
+class CHandler:
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp,
+ CDatabase
+{
+public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+};
+
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ *stream = 0;
+ const CItem &item = Items[index];
+ CClusterInStream *streamSpec = new CClusterInStream;
+ CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
+ streamSpec->Stream = InStream;
+ streamSpec->StartOffset = Header.DataSector << Header.SectorSizeLog;
+ streamSpec->BlockSizeLog = Header.ClusterSizeLog;
+ streamSpec->Size = item.Size;
+
+ UInt32 numClusters = Header.GetNumClusters(item.Size);
+ streamSpec->Vector.Reserve(numClusters);
+ UInt32 cluster = item.Cluster;
+ UInt32 size = item.Size;
+
+ if (size == 0)
+ {
+ if (cluster != 0)
+ return S_FALSE;
+ }
+ else
+ {
+ UInt32 clusterSize = Header.ClusterSize();
+ for (;; size -= clusterSize)
+ {
+ if (!Header.IsValidCluster(cluster))
+ return S_FALSE;
+ streamSpec->Vector.Add(cluster - 2);
+ cluster = Fat[cluster];
+ if (size <= clusterSize)
+ break;
+ }
+ if (!Header.IsEocAndUnused(cluster))
+ return S_FALSE;
+ }
+ RINOK(streamSpec->InitAndSeek());
+ *stream = streamTemp.Detach();
+ return S_OK;
+ COM_TRY_END
+}
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidIsDir, VT_BOOL},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidCTime, VT_FILETIME},
+ { NULL, kpidATime, VT_FILETIME},
+ { NULL, kpidAttrib, VT_UI8},
+ { NULL, kpidShortName, VT_BSTR}
+};
+
+enum
+{
+ kpidNumFats = kpidUserDefined
+ // kpidOemName,
+ // kpidVolName,
+ // kpidFileSysType
+};
+
+STATPROPSTG kArcProps[] =
+{
+ { NULL, kpidFileSystem, VT_BSTR},
+ { NULL, kpidClusterSize, VT_UI4},
+ { NULL, kpidPhySize, VT_UI8},
+ { NULL, kpidFreeSpace, VT_UI8},
+ { NULL, kpidHeadersSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidVolumeName, VT_BSTR},
+
+ { L"FATs", kpidNumFats, VT_UI4},
+ { NULL, kpidSectorSize, VT_UI4},
+ { NULL, kpidId, VT_UI4},
+ // { L"OEM Name", kpidOemName, VT_BSTR},
+ // { L"Volume Name", kpidVolName, VT_BSTR},
+ // { L"File System Type", kpidFileSysType, VT_BSTR}
+ // { NULL, kpidSectorsPerTrack, VT_UI4},
+ // { NULL, kpidNumHeads, VT_UI4},
+ // { NULL, kpidHiddenSectors, VT_UI4}
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_WITH_NAME
+
+static void FatTimeToProp(UInt32 dosTime, UInt32 ms10, NWindows::NCOM::CPropVariant &prop)
+{
+ FILETIME localFileTime, utc;
+ if (NWindows::NTime::DosTimeToFileTime(dosTime, localFileTime))
+ if (LocalFileTimeToFileTime(&localFileTime, &utc))
+ {
+ UInt64 t64 = (((UInt64)utc.dwHighDateTime) << 32) + utc.dwLowDateTime;
+ t64 += ms10 * 100000;
+ utc.dwLowDateTime = (DWORD)t64;
+ utc.dwHighDateTime = (DWORD)(t64 >> 32);
+ prop = utc;
+ }
+}
+
+/*
+static void StringToProp(const Byte *src, int size, NWindows::NCOM::CPropVariant &prop)
+{
+ char dest[32];
+ memcpy(dest, src, size);
+ dest[size] = 0;
+ prop = FatStringToUnicode(dest);
+}
+
+#define STRING_TO_PROP(s, p) StringToProp(s, sizeof(s), prop)
+*/
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidFileSystem:
+ {
+ wchar_t s[32] = { L'F', L'A', L'T' };
+ ConvertUInt32ToString(Header.NumFatBits, s + 3);
+ prop = s;
+ break;
+ }
+ case kpidClusterSize: prop = Header.ClusterSize(); break;
+ case kpidPhySize: prop = Header.GetPhySize(); break;
+ case kpidFreeSpace: prop = (UInt64)NumFreeClusters << Header.ClusterSizeLog; break;
+ case kpidHeadersSize: prop = GetHeadersSize(); break;
+ case kpidMTime: if (VolItemDefined) FatTimeToProp(VolItem.MTime, 0, prop); break;
+ case kpidVolumeName: if (VolItemDefined) prop = VolItem.GetVolName(); break;
+ case kpidNumFats: if (Header.NumFats != 2) prop = Header.NumFats; break;
+ case kpidSectorSize: prop = (UInt32)1 << Header.SectorSizeLog; break;
+ // case kpidSectorsPerTrack: prop = Header.SectorsPerTrack; break;
+ // case kpidNumHeads: prop = Header.NumHeads; break;
+ // case kpidOemName: STRING_TO_PROP(Header.OemName, prop); break;
+ case kpidId: if (Header.VolFieldsDefined) prop = Header.VolId; break;
+ // case kpidVolName: if (Header.VolFieldsDefined) STRING_TO_PROP(Header.VolName, prop); break;
+ // case kpidFileSysType: if (Header.VolFieldsDefined) STRING_TO_PROP(Header.FileSys, prop); break;
+ // case kpidHiddenSectors: prop = Header.NumHiddenSectors; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ const CItem &item = Items[index];
+ switch(propID)
+ {
+ case kpidPath: prop = GetItemPath(index); break;
+ case kpidShortName: prop = item.GetShortName(); break;
+ case kpidIsDir: prop = item.IsDir(); break;
+ case kpidMTime: FatTimeToProp(item.MTime, 0, prop); break;
+ case kpidCTime: FatTimeToProp(item.CTime, item.CTime2, prop); break;
+ case kpidATime: FatTimeToProp(((UInt32)item.ADate << 16), 0, prop); break;
+ case kpidAttrib: prop = (UInt32)item.Attrib; break;
+ case kpidSize: if (!item.IsDir()) prop = item.Size; break;
+ case kpidPackSize: if (!item.IsDir()) prop = Header.GetFilePackSize(item.Size); break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream, const UInt64 *, IArchiveOpenCallback *callback)
+{
+ COM_TRY_BEGIN
+ {
+ OpenCallback = callback;
+ InStream = stream;
+ HRESULT res;
+ try
+ {
+ res = CDatabase::Open();
+ if (res == S_OK)
+ return S_OK;
+ }
+ catch(...)
+ {
+ Close();
+ throw;
+ }
+ Close();
+ return res;
+ }
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ ClearAndClose();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool testMode = (_aTestMode != 0);
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (allFilesMode)
+ numItems = Items.Size();
+ if (numItems == 0)
+ return S_OK;
+ UInt32 i;
+ UInt64 totalSize = 0;
+ for (i = 0; i < numItems; i++)
+ {
+ const CItem &item = Items[allFilesMode ? i : indices[i]];
+ if (!item.IsDir())
+ totalSize += item.Size;
+ }
+ RINOK(extractCallback->SetTotal(totalSize));
+
+ UInt64 totalPackSize;
+ totalSize = totalPackSize = 0;
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+
+ for (i = 0; i < numItems; i++)
+ {
+ lps->InSize = totalPackSize;
+ lps->OutSize = totalSize;
+ RINOK(lps->SetCur());
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ Int32 index = allFilesMode ? i : indices[i];
+ const CItem &item = Items[index];
+ RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
+
+ if (item.IsDir())
+ {
+ RINOK(extractCallback->PrepareOperation(askMode));
+ RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
+ continue;
+ }
+
+ totalPackSize += Header.GetFilePackSize(item.Size);
+ totalSize += item.Size;
+
+ if (!testMode && (!realOutStream))
+ continue;
+ RINOK(extractCallback->PrepareOperation(askMode));
+
+ outStreamSpec->SetStream(realOutStream);
+ realOutStream.Release();
+ outStreamSpec->Init();
+
+ int res = NArchive::NExtract::NOperationResult::kDataError;
+ CMyComPtr<ISequentialInStream> inStream;
+ HRESULT hres = GetStream(index, &inStream);
+ if (hres != S_FALSE)
+ {
+ RINOK(hres);
+ if (inStream)
+ {
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ if (copyCoderSpec->TotalSize == item.Size)
+ res = NArchive::NExtract::NOperationResult::kOK;
+ }
+ }
+ outStreamSpec->ReleaseStream();
+ RINOK(extractCallback->SetOperationResult(res));
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = Items.Size();
+ return S_OK;
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"FAT", L"fat img", 0, 0xDA, { 0x55, 0xAA }, 2, false, CreateArc, 0 };
+
+REGISTER_ARC(Fat)
+
+}}
diff --git a/CPP/7zip/Archive/GZip/GZipHandler.cpp b/CPP/7zip/Archive/GZip/GZipHandler.cpp
deleted file mode 100755
index 96ae85f1..00000000
--- a/CPP/7zip/Archive/GZip/GZipHandler.cpp
+++ /dev/null
@@ -1,284 +0,0 @@
-// GZipHandler.cpp
-
-#include "StdAfx.h"
-
-#include "GZipHandler.h"
-
-#include "Common/Defs.h"
-#include "Common/StringConvert.h"
-#include "Common/ComTry.h"
-#include "Windows/PropVariant.h"
-#include "Windows/Time.h"
-
-#include "../../ICoder.h"
-#include "../../Common/ProgressUtils.h"
-#include "../../Common/CreateCoder.h"
-#include "../Common/OutStreamWithCRC.h"
-
-using namespace NWindows;
-
-namespace NArchive {
-namespace NGZip {
-
-static const CMethodId kMethodId_Deflate = 0x040108;
-
-const wchar_t *kHostOS[] =
-{
- L"FAT",
- L"AMIGA",
- L"VMS",
- L"Unix",
- L"VM_CMS",
- L"Atari", // what if it's a minix filesystem? [cjh]
- L"HPFS", // filesystem used by OS/2 (and NT 3.x)
- L"Mac",
- L"Z_System",
- L"CPM",
- L"TOPS20", // pkzip 2.50 NTFS
- L"NTFS", // filesystem used by Windows NT
- L"QDOS ", // SMS/QDOS
- L"Acorn", // Archimedes Acorn RISC OS
- L"VFAT", // filesystem used by Windows 95, NT
- L"MVS",
- L"BeOS", // hybrid POSIX/database filesystem
- // BeBOX or PowerMac
- L"Tandem",
- L"THEOS"
-};
-
-static const int kNumHostOSes = sizeof(kHostOS) / sizeof(kHostOS[0]);
-
-static const wchar_t *kUnknownOS = L"Unknown";
-
-/*
-enum // PropID
-{
- kpidExtraIsPresent = kpidUserDefined,
- kpidExtraFlags,
- kpidIsText
-};
-*/
-
-STATPROPSTG kProps[] =
-{
- { NULL, kpidPath, VT_BSTR},
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
- { NULL, kpidMTime, VT_FILETIME},
- // { NULL, kpidMethod, VT_UI1},
- { NULL, kpidHostOS, VT_BSTR},
- { NULL, kpidCRC, VT_UI4}
- // { L"Extra", kpidExtraIsPresent, VT_BOOL}
- // { L"Extra flags", kpidExtraFlags, VT_UI1},
- // { L"Is Text", kpidIsText, VT_BOOL},
-};
-
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
-
-STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
-{
- *numItems = 1;
- return S_OK;
-}
-
-STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
-{
- COM_TRY_BEGIN
- NWindows::NCOM::CPropVariant prop;
- switch(propID)
- {
- case kpidPath:
- if (m_Item.NameIsPresent())
- prop = MultiByteToUnicodeString(m_Item.Name, CP_ACP);
- break;
- case kpidMTime:
- {
- FILETIME utcTime;
- if (m_Item.Time != 0)
- {
- NTime::UnixTimeToFileTime((UInt32)m_Item.Time, utcTime);
- prop = utcTime;
- }
- else
- {
- // utcTime.dwLowDateTime = utcTime.dwHighDateTime = 0;
- // prop = utcTime;
- }
- break;
- }
- case kpidSize: prop = UInt64(m_Item.UnPackSize32); break;
- case kpidPackSize: prop = m_PackSize; break;
- case kpidCommented: prop = m_Item.CommentIsPresent(); break;
- case kpidHostOS:
- prop = (m_Item.HostOS < kNumHostOSes) ?
- kHostOS[m_Item.HostOS] : kUnknownOS;
- break;
- case kpidMethod: prop = m_Item.CompressionMethod; break;
- case kpidCRC: prop = m_Item.FileCRC; break;
- /*
- case kpidExtraFlags: prop = m_Item.ExtraFlags; break;
- case kpidIsText: prop = m_Item.IsText(); break;
- case kpidExtraIsPresent: prop = m_Item.ExtraFieldIsPresent(); break;
- */
- }
- prop.Detach(value);
- return S_OK;
- COM_TRY_END
-}
-
-STDMETHODIMP CHandler::Open(IInStream *inStream,
- const UInt64 * /* maxCheckStartPosition */,
- IArchiveOpenCallback * /* openArchiveCallback */)
-{
- COM_TRY_BEGIN
- try
- {
- CInArchive archive;
- RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_StreamStartPosition));
- RINOK(archive.ReadHeader(inStream, m_Item));
- m_DataOffset = archive.GetOffset();
- UInt64 newPosition;
- RINOK(inStream->Seek(-8, STREAM_SEEK_END, &newPosition));
- m_PackSize = newPosition - (m_StreamStartPosition + m_DataOffset);
- if (archive.ReadPostHeader(inStream, m_Item) != S_OK)
- return S_FALSE;
- m_Stream = inStream;
- }
- catch(...)
- {
- return S_FALSE;
- }
- return S_OK;
- COM_TRY_END
-}
-
-STDMETHODIMP CHandler::Close()
-{
- m_Stream.Release();
- return S_OK;
-}
-
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
-{
- COM_TRY_BEGIN
- bool allFilesMode = (numItems == UInt32(-1));
- if (!allFilesMode)
- {
- if (numItems == 0)
- return S_OK;
- if (numItems != 1)
- return E_INVALIDARG;
- if (indices[0] != 0)
- return E_INVALIDARG;
- }
-
- bool testMode = (_aTestMode != 0);
-
- extractCallback->SetTotal(m_PackSize);
-
- UInt64 currentTotalPacked = 0;
-
- RINOK(extractCallback->SetCompleted(&currentTotalPacked));
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode;
- askMode = testMode ? NArchive::NExtract::NAskMode::kTest :
- NArchive::NExtract::NAskMode::kExtract;
-
- RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
-
- if(!testMode && !realOutStream)
- return S_OK;
-
- extractCallback->PrepareOperation(askMode);
-
- COutStreamWithCRC *outStreamSpec = new COutStreamWithCRC;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
- realOutStream.Release();
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(extractCallback, true);
-
- CMyComPtr<ICompressCoder> deflateDecoder;
- bool firstItem = true;
- RINOK(m_Stream->Seek(m_StreamStartPosition, STREAM_SEEK_SET, NULL));
- Int32 opRes;
- for (;;)
- {
- lps->InSize = currentTotalPacked;
- lps->OutSize = outStreamSpec->GetSize();
-
- CInArchive archive;
- CItem item;
- HRESULT result = archive.ReadHeader(m_Stream, item);
- if (result != S_OK)
- {
- if (firstItem)
- return E_FAIL;
- opRes = NArchive::NExtract::NOperationResult::kOK;
- break;
- }
- firstItem = false;
-
- UInt64 dataStartPos;
- RINOK(m_Stream->Seek(0, STREAM_SEEK_CUR, &dataStartPos));
-
- outStreamSpec->InitCRC();
-
- if (item.CompressionMethod != NFileHeader::NCompressionMethod::kDeflate)
- {
- opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
- break;
- }
-
- if (!deflateDecoder)
- {
- RINOK(CreateCoder(
- EXTERNAL_CODECS_VARS
- kMethodId_Deflate, deflateDecoder, false));
- if (!deflateDecoder)
- {
- opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
- break;
- }
- }
- result = deflateDecoder->Code(m_Stream, outStream, NULL, NULL, progress);
- if (result != S_OK)
- {
- if (result != S_FALSE)
- return result;
- opRes = NArchive::NExtract::NOperationResult::kDataError;
- break;
- }
-
- CMyComPtr<ICompressGetInStreamProcessedSize> getInStreamProcessedSize;
- RINOK(deflateDecoder.QueryInterface(IID_ICompressGetInStreamProcessedSize,
- &getInStreamProcessedSize));
- UInt64 packSize;
- RINOK(getInStreamProcessedSize->GetInStreamProcessedSize(&packSize));
- UInt64 pos;
- RINOK(m_Stream->Seek(dataStartPos + packSize, STREAM_SEEK_SET, &pos));
-
- currentTotalPacked = pos - m_StreamStartPosition;
-
- CItem postItem;
- if (archive.ReadPostHeader(m_Stream, postItem) != S_OK)
- return E_FAIL;
- if((outStreamSpec->GetCRC() != postItem.FileCRC))
- {
- opRes = NArchive::NExtract::NOperationResult::kCRCError;
- break;
- }
- }
- outStream.Release();
- return extractCallback->SetOperationResult(opRes);
- COM_TRY_END
-}
-
-IMPL_ISetCompressCodecsInfo
-
-}}
diff --git a/CPP/7zip/Archive/GZip/GZipHandler.h b/CPP/7zip/Archive/GZip/GZipHandler.h
deleted file mode 100755
index 49a01a8d..00000000
--- a/CPP/7zip/Archive/GZip/GZipHandler.h
+++ /dev/null
@@ -1,63 +0,0 @@
-// GZip/Handler.h
-
-#ifndef __GZIP_HANDLER_H
-#define __GZIP_HANDLER_H
-
-#include "Common/MyCom.h"
-
-#include "../IArchive.h"
-
-#include "../../Common/CreateCoder.h"
-
-#include "GZipIn.h"
-#include "GZipUpdate.h"
-
-namespace NArchive {
-namespace NGZip {
-
-class CHandler:
- public IInArchive,
- public IOutArchive,
- public ISetProperties,
- PUBLIC_ISetCompressCodecsInfo
- public CMyUnknownImp
-{
-public:
- MY_QUERYINTERFACE_BEGIN2(IInArchive)
- MY_QUERYINTERFACE_ENTRY(IOutArchive)
- MY_QUERYINTERFACE_ENTRY(ISetProperties)
- QUERY_ENTRY_ISetCompressCodecsInfo
- MY_QUERYINTERFACE_END
- MY_ADDREF_RELEASE
-
- INTERFACE_IInArchive(;)
- INTERFACE_IOutArchive(;)
-
- STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties);
-
- DECL_ISetCompressCodecsInfo
-
- CHandler() { InitMethodProperties(); }
-
-private:
- NArchive::NGZip::CItem m_Item;
- UInt64 m_StreamStartPosition;
- UInt64 m_DataOffset;
- UInt64 m_PackSize;
- CMyComPtr<IInStream> m_Stream;
- CCompressionMethodMode m_Method;
- UInt32 m_Level;
-
- DECL_EXTERNAL_CODECS_VARS
-
- void InitMethodProperties()
- {
- m_Method.NumMatchFinderCyclesDefined = false;
- m_Level = m_Method.NumPasses = m_Method.NumFastBytes =
- m_Method.NumMatchFinderCycles = m_Method.Algo = 0xFFFFFFFF;
- }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/GZipHandlerOut.cpp b/CPP/7zip/Archive/GZip/GZipHandlerOut.cpp
deleted file mode 100755
index bcbfc7e2..00000000
--- a/CPP/7zip/Archive/GZip/GZipHandlerOut.cpp
+++ /dev/null
@@ -1,202 +0,0 @@
-// GZipHandlerOut.cpp
-
-#include "StdAfx.h"
-
-#include "Common/StringConvert.h"
-#include "Common/StringToInt.h"
-
-#include "Windows/PropVariant.h"
-#include "Windows/Time.h"
-
-#include "../../Compress/CopyCoder.h"
-
-#include "../Common/ParseProperties.h"
-
-#include "GZipHandler.h"
-#include "GZipUpdate.h"
-
-using namespace NWindows;
-using namespace NTime;
-
-namespace NArchive {
-namespace NGZip {
-
-static const UInt32 kAlgoX1 = 0;
-static const UInt32 kAlgoX5 = 1;
-
-static const UInt32 kNumPassesX1 = 1;
-static const UInt32 kNumPassesX7 = 3;
-static const UInt32 kNumPassesX9 = 10;
-
-static const UInt32 kNumFastBytesX1 = 32;
-static const UInt32 kNumFastBytesX7 = 64;
-static const UInt32 kNumFastBytesX9 = 128;
-
-
-STDMETHODIMP CHandler::GetFileTimeType(UInt32 *timeType)
-{
- *timeType = NFileTimeType::kUnix;
- return S_OK;
-}
-
-static HRESULT CopyStreams(ISequentialInStream *inStream, ISequentialOutStream *outStream)
-{
- CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
- return copyCoder->Code(inStream, outStream, NULL, NULL, NULL);
-}
-
-STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
- IArchiveUpdateCallback *updateCallback)
-{
- if (numItems != 1)
- return E_INVALIDARG;
-
- UInt64 size;
- Int32 newData;
- Int32 newProperties;
- UInt32 indexInArchive;
- UInt32 itemIndex = 0;
- if (!updateCallback)
- return E_FAIL;
- RINOK(updateCallback->GetUpdateItemInfo(0, &newData, &newProperties, &indexInArchive));
-
- CItem newItem = m_Item;
- newItem.ExtraFlags = 0;
- newItem.Flags = 0;
- if (IntToBool(newProperties))
- {
- FILETIME utcTime;
- UString name;
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(itemIndex, kpidMTime, &prop));
- if (prop.vt != VT_FILETIME)
- return E_INVALIDARG;
- utcTime = prop.filetime;
- }
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(itemIndex, kpidPath, &prop));
- if (prop.vt == VT_EMPTY)
- name.Empty();
- else if (prop.vt != VT_BSTR)
- return E_INVALIDARG;
- else
- name = prop.bstrVal;
- }
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(itemIndex, kpidIsDir, &prop));
- if (prop.vt == VT_BOOL)
- {
- if (prop.boolVal != VARIANT_FALSE)
- return E_INVALIDARG;
- }
- else if (prop.vt != VT_EMPTY)
- return E_INVALIDARG;
- }
- if(!FileTimeToUnixTime(utcTime, newItem.Time))
- return E_INVALIDARG;
- newItem.Name = UnicodeStringToMultiByte(name, CP_ACP);
- int dirDelimiterPos = newItem.Name.ReverseFind(CHAR_PATH_SEPARATOR);
- if (dirDelimiterPos >= 0)
- newItem.Name = newItem.Name.Mid(dirDelimiterPos + 1);
-
- newItem.SetNameIsPresentFlag(!newItem.Name.IsEmpty());
- }
-
- if (IntToBool(newData))
- {
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(itemIndex, kpidSize, &prop));
- if (prop.vt != VT_UI8)
- return E_INVALIDARG;
- size = prop.uhVal.QuadPart;
- }
- newItem.UnPackSize32 = (UInt32)size;
-
- UInt32 level = m_Level;
- if (level == 0xFFFFFFFF)
- level = 5;
- if (m_Method.NumPasses == 0xFFFFFFFF)
- m_Method.NumPasses = (level >= 9 ? kNumPassesX9 :
- (level >= 7 ? kNumPassesX7 :
- kNumPassesX1));
- if (m_Method.NumFastBytes == 0xFFFFFFFF)
- m_Method.NumFastBytes = (level >= 9 ? kNumFastBytesX9 :
- (level >= 7 ? kNumFastBytesX7 :
- kNumFastBytesX1));
- if (m_Method.Algo == 0xFFFFFFFF)
- m_Method.Algo =
- (level >= 5 ? kAlgoX5 :
- kAlgoX1);
-
- return UpdateArchive(
- EXTERNAL_CODECS_VARS
- m_Stream, size, outStream, newItem, m_Method, itemIndex, updateCallback);
- }
-
- if (indexInArchive != 0)
- return E_INVALIDARG;
-
- if (IntToBool(newProperties))
- {
- COutArchive outArchive;
- outArchive.Create(outStream);
- outArchive.WriteHeader(newItem);
- RINOK(m_Stream->Seek(m_StreamStartPosition + m_DataOffset, STREAM_SEEK_SET, NULL));
- }
- else
- {
- RINOK(m_Stream->Seek(m_StreamStartPosition, STREAM_SEEK_SET, NULL));
- }
- return CopyStreams(m_Stream, outStream);
-}
-
-STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties)
-{
- InitMethodProperties();
- for (int i = 0; i < numProperties; i++)
- {
- UString name = names[i];
- name.MakeUpper();
- const PROPVARIANT &prop = values[i];
- if (name[0] == L'X')
- {
- UInt32 level = 9;
- RINOK(ParsePropValue(name.Mid(1), prop, level));
- m_Level = level;
- }
- else if (name.Left(4) == L"PASS")
- {
- UInt32 num = kNumPassesX9;
- RINOK(ParsePropValue(name.Mid(4), prop, num));
- m_Method.NumPasses = num;
- }
- else if (name.Left(2) == L"FB")
- {
- UInt32 num = kNumFastBytesX9;
- RINOK(ParsePropValue(name.Mid(2), prop, num));
- m_Method.NumFastBytes = num;
- }
- else if (name.Left(2) == L"MC")
- {
- UInt32 num = 0xFFFFFFFF;
- RINOK(ParsePropValue(name.Mid(2), prop, num));
- m_Method.NumMatchFinderCycles = num;
- m_Method.NumMatchFinderCyclesDefined = true;
- }
- else if (name.Left(1) == L"A")
- {
- UInt32 num = kAlgoX5;
- RINOK(ParsePropValue(name.Mid(1), prop, num));
- m_Method.Algo = num;
- }
- else
- return E_INVALIDARG;
- }
- return S_OK;
-}
-
-}}
diff --git a/CPP/7zip/Archive/GZip/GZipHeader.cpp b/CPP/7zip/Archive/GZip/GZipHeader.cpp
deleted file mode 100755
index 88b34e86..00000000
--- a/CPP/7zip/Archive/GZip/GZipHeader.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
-// Archive/GZip/Header.h
-
-#include "StdAfx.h"
-
-#include "GZipHeader.h"
-
-namespace NArchive {
-namespace NGZip {
-
-extern UInt16 kSignature = 0x8B1F + 1;
-
-static class CMarkersInitializer
-{
-public:
- CMarkersInitializer()
- { kSignature--; }
-} g_MarkerInitializer;
-
-}}
-
diff --git a/CPP/7zip/Archive/GZip/GZipHeader.h b/CPP/7zip/Archive/GZip/GZipHeader.h
deleted file mode 100755
index 010a60aa..00000000
--- a/CPP/7zip/Archive/GZip/GZipHeader.h
+++ /dev/null
@@ -1,85 +0,0 @@
-// Archive/GZip/Header.h
-
-#ifndef __ARCHIVE_GZIP_HEADER_H
-#define __ARCHIVE_GZIP_HEADER_H
-
-#include "Common/Types.h"
-
-namespace NArchive {
-namespace NGZip {
-
-extern UInt16 kSignature;
-static const UInt32 kSignatureSize = 2;
-
-namespace NFileHeader
-{
- /*
- struct CBlock
- {
- UInt16 Id;
- Byte CompressionMethod;
- Byte Flags;
- UInt32 Time;
- Byte ExtraFlags;
- Byte HostOS;
- };
- */
-
- namespace NFlags
- {
- const int kDataIsText = 1 << 0;
- const int kHeaderCRCIsPresent = 1 << 1;
- const int kExtraIsPresent = 1 << 2;
- const int kNameIsPresent = 1 << 3;
- const int kComentIsPresent = 1 << 4;
- }
-
- namespace NExtraFlags
- {
- enum EEnum
- {
- kMaximum = 2,
- kFastest = 4
- };
- }
-
- namespace NCompressionMethod
- {
- const Byte kDeflate = 8;
- }
-
- namespace NHostOS
- {
- enum EEnum
- {
- kFAT = 0, // filesystem used by MS-DOS, OS/2, Win32
- // pkzip 2.50 (FAT / VFAT / FAT32 file systems)
- kAMIGA = 1,
- kVMS = 2, // VAX/VMS
- kUnix = 3,
- kVM_CMS = 4,
- kAtari = 5, // what if it's a minix filesystem? [cjh]
- kHPFS = 6, // filesystem used by OS/2 (and NT 3.x)
- kMac = 7,
- kZ_System = 8,
- kCPM = 9,
- kTOPS20 = 10, // pkzip 2.50 NTFS
- kNTFS = 11, // filesystem used by Windows NT
- kQDOS = 12, // SMS/QDOS
- kAcorn = 13, // Archimedes Acorn RISC OS
- kVFAT = 14, // filesystem used by Windows 95, NT
- kMVS = 15,
- kBeOS = 16, // hybrid POSIX/database filesystem
- // BeBOX or PowerMac
- kTandem = 17,
- kTHEOS = 18,
-
- kUnknown = 255
- };
- const int kNumHostSystems = 19;
- }
-}
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/GZipIn.cpp b/CPP/7zip/Archive/GZip/GZipIn.cpp
deleted file mode 100755
index d754c045..00000000
--- a/CPP/7zip/Archive/GZip/GZipIn.cpp
+++ /dev/null
@@ -1,119 +0,0 @@
-// Archive/GZipIn.cpp
-
-#include "StdAfx.h"
-
-#include "GZipIn.h"
-
-#include "Common/Defs.h"
-#include "Common/MyCom.h"
-#include "Windows/Defs.h"
-
-#include "../../Common/StreamUtils.h"
-
-extern "C"
-{
- #include "../../../../C/7zCrc.h"
-}
-
-namespace NArchive {
-namespace NGZip {
-
-HRESULT CInArchive::ReadBytes(ISequentialInStream *inStream, void *data, UInt32 size)
-{
- RINOK(ReadStream_FALSE(inStream, data, size));
- m_Position += size;
- return S_OK;
-}
-
-HRESULT CInArchive::ReadByte(ISequentialInStream *inStream, Byte &value, UInt32 &crc)
-{
- RINOK(ReadBytes(inStream, &value, 1));
- crc = CRC_UPDATE_BYTE(crc, value);
- return S_OK;
-}
-
-HRESULT CInArchive::ReadUInt16(ISequentialInStream *inStream, UInt16 &value, UInt32 &crc)
-{
- value = 0;
- for (int i = 0; i < 2; i++)
- {
- Byte b;
- RINOK(ReadByte(inStream, b, crc));
- value |= (UInt16(b) << (8 * i));
- }
- return S_OK;
-}
-
-HRESULT CInArchive::ReadUInt32(ISequentialInStream *inStream, UInt32 &value, UInt32 &crc)
-{
- value = 0;
- for (int i = 0; i < 4; i++)
- {
- Byte b;
- RINOK(ReadByte(inStream, b, crc));
- value |= (UInt32(b) << (8 * i));
- }
- return S_OK;
-}
-
-HRESULT CInArchive::ReadZeroTerminatedString(ISequentialInStream *inStream, AString &resString, UInt32 &crc)
-{
- resString.Empty();
- for (;;)
- {
- Byte c;
- RINOK(ReadByte(inStream, c, crc));
- if (c == 0)
- return S_OK;
- resString += char(c);
- }
-}
-
-HRESULT CInArchive::ReadHeader(ISequentialInStream *inStream, CItem &item)
-{
- item.Clear();
- m_Position = 0;
-
- UInt16 signature;
- UInt32 crc = CRC_INIT_VAL;;
- RINOK(ReadUInt16(inStream, signature, crc));
- if (signature != kSignature)
- return S_FALSE;
-
- RINOK(ReadByte(inStream, item.CompressionMethod, crc));
- RINOK(ReadByte(inStream, item.Flags, crc));
- RINOK(ReadUInt32(inStream, item.Time, crc));
- RINOK(ReadByte(inStream, item.ExtraFlags, crc));
- RINOK(ReadByte(inStream, item.HostOS, crc));
-
- if (item.ExtraFieldIsPresent())
- {
- UInt16 extraSize;
- RINOK(ReadUInt16(inStream, extraSize, crc));
- item.Extra.SetCapacity(extraSize);
- RINOK(ReadBytes(inStream, item.Extra, extraSize));
- crc = CrcUpdate(crc, item.Extra, extraSize);
- }
- if (item.NameIsPresent())
- RINOK(ReadZeroTerminatedString(inStream, item.Name, crc));
- if (item.CommentIsPresent())
- RINOK(ReadZeroTerminatedString(inStream, item.Comment, crc));
- if (item.HeaderCRCIsPresent())
- {
- UInt16 headerCRC;
- UInt32 dummy = 0;
- RINOK(ReadUInt16(inStream, headerCRC, dummy));
- if ((UInt16)CRC_GET_DIGEST(crc) != headerCRC)
- return S_FALSE;
- }
- return S_OK;
-}
-
-HRESULT CInArchive::ReadPostHeader(ISequentialInStream *inStream, CItem &item)
-{
- UInt32 dummy = 0;
- RINOK(ReadUInt32(inStream, item.FileCRC, dummy));
- return ReadUInt32(inStream, item.UnPackSize32, dummy);
-}
-
-}}
diff --git a/CPP/7zip/Archive/GZip/GZipIn.h b/CPP/7zip/Archive/GZip/GZipIn.h
deleted file mode 100755
index c2e07490..00000000
--- a/CPP/7zip/Archive/GZip/GZipIn.h
+++ /dev/null
@@ -1,30 +0,0 @@
-// Archive/GZipIn.h
-
-#ifndef __ARCHIVE_GZIP_IN_H
-#define __ARCHIVE_GZIP_IN_H
-
-#include "GZipHeader.h"
-#include "GZipItem.h"
-#include "../../IStream.h"
-
-namespace NArchive {
-namespace NGZip {
-
-class CInArchive
-{
- UInt64 m_Position;
-
- HRESULT ReadBytes(ISequentialInStream *inStream, void *data, UInt32 size);
- HRESULT ReadZeroTerminatedString(ISequentialInStream *inStream, AString &resString, UInt32 &crc);
- HRESULT ReadByte(ISequentialInStream *inStream, Byte &value, UInt32 &crc);
- HRESULT ReadUInt16(ISequentialInStream *inStream, UInt16 &value, UInt32 &crc);
- HRESULT ReadUInt32(ISequentialInStream *inStream, UInt32 &value, UInt32 &crc);
-public:
- HRESULT ReadHeader(ISequentialInStream *inStream, CItem &item);
- HRESULT ReadPostHeader(ISequentialInStream *inStream, CItem &item);
- UInt64 GetOffset() const { return m_Position; }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/GZipItem.h b/CPP/7zip/Archive/GZip/GZipItem.h
deleted file mode 100755
index 678962a9..00000000
--- a/CPP/7zip/Archive/GZip/GZipItem.h
+++ /dev/null
@@ -1,59 +0,0 @@
-// Archive/GZipItem.h
-
-#ifndef __ARCHIVE_GZIP_ITEM_H
-#define __ARCHIVE_GZIP_ITEM_H
-
-#include "Common/Types.h"
-#include "Common/MyString.h"
-#include "Common/Buffer.h"
-
-namespace NArchive {
-namespace NGZip {
-
-class CItem
-{
-private:
- bool TestFlag(Byte flag) const { return ((Flags & flag) != 0); }
-public:
- Byte CompressionMethod;
- Byte Flags;
- UInt32 Time;
- Byte ExtraFlags;
- Byte HostOS;
- UInt32 FileCRC;
- UInt32 UnPackSize32;
-
- AString Name;
- AString Comment;
- CByteBuffer Extra;
-
- bool IsText() const
- { return TestFlag(NFileHeader::NFlags::kDataIsText); }
- bool HeaderCRCIsPresent() const
- { return TestFlag(NFileHeader::NFlags::kHeaderCRCIsPresent); }
- bool ExtraFieldIsPresent() const
- { return TestFlag(NFileHeader::NFlags::kExtraIsPresent); }
- bool NameIsPresent() const
- { return TestFlag(NFileHeader::NFlags::kNameIsPresent); }
- bool CommentIsPresent() const
- { return TestFlag(NFileHeader::NFlags::kComentIsPresent); }
-
- void SetNameIsPresentFlag(bool nameIsPresent)
- {
- if (nameIsPresent)
- Flags |= NFileHeader::NFlags::kNameIsPresent;
- else
- Flags &= (~NFileHeader::NFlags::kNameIsPresent);
- }
-
- void Clear()
- {
- Name.Empty();
- Comment.Empty();;
- Extra.SetCapacity(0);
- }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/GZipOut.cpp b/CPP/7zip/Archive/GZip/GZipOut.cpp
deleted file mode 100755
index 3d0d4f7a..00000000
--- a/CPP/7zip/Archive/GZip/GZipOut.cpp
+++ /dev/null
@@ -1,65 +0,0 @@
-// Archive/GZipOut.cpp
-
-#include "StdAfx.h"
-
-#include "GZipOut.h"
-
-#include "Windows/Defs.h"
-#include "../../Common/StreamUtils.h"
-
-namespace NArchive {
-namespace NGZip {
-
-HRESULT COutArchive::WriteBytes(const void *buffer, UInt32 size)
-{
- return WriteStream(m_Stream, buffer, size);
-}
-
-HRESULT COutArchive::WriteByte(Byte value)
-{
- return WriteBytes(&value, 1);
-}
-
-HRESULT COutArchive::WriteUInt16(UInt16 value)
-{
- for (int i = 0; i < 2; i++)
- {
- RINOK(WriteByte((Byte)value));
- value >>= 8;
- }
- return S_OK;
-}
-
-HRESULT COutArchive::WriteUInt32(UInt32 value)
-{
- for (int i = 0; i < 4; i++)
- {
- RINOK(WriteByte((Byte)value));
- value >>= 8;
- }
- return S_OK;
-}
-
-HRESULT COutArchive::WriteHeader(const CItem &item)
-{
- RINOK(WriteUInt16(kSignature));
- RINOK(WriteByte(item.CompressionMethod));
- RINOK(WriteByte((Byte)(item.Flags & NFileHeader::NFlags::kNameIsPresent)));
- RINOK(WriteUInt32(item.Time));
- RINOK(WriteByte(item.ExtraFlags));
- RINOK(WriteByte(item.HostOS));
- if (item.NameIsPresent())
- {
- RINOK(WriteBytes((const char *)item.Name, item.Name.Length()));
- RINOK(WriteByte(0));
- }
- return S_OK;
-}
-
-HRESULT COutArchive::WritePostHeader(const CItem &item)
-{
- RINOK(WriteUInt32(item.FileCRC));
- return WriteUInt32(item.UnPackSize32);
-}
-
-}}
diff --git a/CPP/7zip/Archive/GZip/GZipOut.h b/CPP/7zip/Archive/GZip/GZipOut.h
deleted file mode 100755
index a2ba2ebf..00000000
--- a/CPP/7zip/Archive/GZip/GZipOut.h
+++ /dev/null
@@ -1,29 +0,0 @@
-// Archive/GZipOut.h
-
-#ifndef __ARCHIVE_GZIP_OUT_H
-#define __ARCHIVE_GZIP_OUT_H
-
-#include "Common/MyCom.h"
-#include "GZipHeader.h"
-#include "GZipItem.h"
-#include "../../IStream.h"
-
-namespace NArchive {
-namespace NGZip {
-
-class COutArchive
-{
- CMyComPtr<ISequentialOutStream> m_Stream;
- HRESULT WriteBytes(const void *buffer, UInt32 size);
- HRESULT WriteByte(Byte value);
- HRESULT WriteUInt16(UInt16 value);
- HRESULT WriteUInt32(UInt32 value);
-public:
- void Create(ISequentialOutStream *outStream) { m_Stream = outStream; }
- HRESULT WriteHeader(const CItem &item);
- HRESULT WritePostHeader(const CItem &item);
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/GZipRegister.cpp b/CPP/7zip/Archive/GZip/GZipRegister.cpp
deleted file mode 100755
index b4bc6ded..00000000
--- a/CPP/7zip/Archive/GZip/GZipRegister.cpp
+++ /dev/null
@@ -1,18 +0,0 @@
-// GZipRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "GZipHandler.h"
-static IInArchive *CreateArc() { return new NArchive::NGZip::CHandler; }
-#ifndef EXTRACT_ONLY
-static IOutArchive *CreateArcOut() { return new NArchive::NGZip::CHandler; }
-#else
-#define CreateArcOut 0
-#endif
-
-static CArcInfo g_ArcInfo =
- { L"GZip", L"gz gzip tgz tpz", L"* * .tar .tar", 0xEF, { 0x1F, 0x8B, 8 }, 3, true, CreateArc, CreateArcOut };
-
-REGISTER_ARC(GZip)
diff --git a/CPP/7zip/Archive/GZip/GZipUpdate.cpp b/CPP/7zip/Archive/GZip/GZipUpdate.cpp
deleted file mode 100755
index f3a4d331..00000000
--- a/CPP/7zip/Archive/GZip/GZipUpdate.cpp
+++ /dev/null
@@ -1,112 +0,0 @@
-// GZipUpdate.cpp
-
-#include "StdAfx.h"
-
-#include "Common/Defs.h"
-#include "Common/StringConvert.h"
-
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
-
-#include "../../ICoder.h"
-
-#include "../../Common/CreateCoder.h"
-#include "../../Common/ProgressUtils.h"
-
-#include "../../Compress/CopyCoder.h"
-
-#include "../Common/InStreamWithCRC.h"
-
-#include "GZipUpdate.h"
-
-namespace NArchive {
-namespace NGZip {
-
-static const CMethodId kMethodId_Deflate = 0x040108;
-
-static const Byte kHostOS =
- #ifdef _WIN32
- NFileHeader::NHostOS::kFAT;
- #else
- NFileHeader::NHostOS::kUnix;
- #endif
-
-HRESULT UpdateArchive(
- DECL_EXTERNAL_CODECS_LOC_VARS
- IInStream * /* inStream */,
- UInt64 unpackSize,
- ISequentialOutStream *outStream,
- const CItem &newItem,
- const CCompressionMethodMode &compressionMethod,
- int indexInClient,
- IArchiveUpdateCallback *updateCallback)
-{
- UInt64 complexity = unpackSize;
-
- RINOK(updateCallback->SetTotal(complexity));
-
- CMyComPtr<ICompressCoder> deflateEncoder;
-
- complexity = 0;
- RINOK(updateCallback->SetCompleted(&complexity));
-
- CMyComPtr<ISequentialInStream> fileInStream;
-
- RINOK(updateCallback->GetStream(indexInClient, &fileInStream));
-
- CSequentialInStreamWithCRC *inStreamSpec = new CSequentialInStreamWithCRC;
- CMyComPtr<ISequentialInStream> crcStream(inStreamSpec);
- inStreamSpec->SetStream(fileInStream);
- inStreamSpec->Init();
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(updateCallback, true);
-
- COutArchive outArchive;
- outArchive.Create(outStream);
-
- CItem item = newItem;
- item.CompressionMethod = NFileHeader::NCompressionMethod::kDeflate;
- item.ExtraFlags = 0;
- item.HostOS = kHostOS;
-
- RINOK(outArchive.WriteHeader(item));
-
- {
- RINOK(CreateCoder(
- EXTERNAL_CODECS_LOC_VARS
- kMethodId_Deflate, deflateEncoder, true));
- if (!deflateEncoder)
- return E_NOTIMPL;
-
- NWindows::NCOM::CPropVariant properties[] =
- {
- compressionMethod.Algo,
- compressionMethod.NumPasses,
- compressionMethod.NumFastBytes,
- compressionMethod.NumMatchFinderCycles
- };
- PROPID propIDs[] =
- {
- NCoderPropID::kAlgorithm,
- NCoderPropID::kNumPasses,
- NCoderPropID::kNumFastBytes,
- NCoderPropID::kMatchFinderCycles
- };
- int numProps = sizeof(propIDs) / sizeof(propIDs[0]);
- if (!compressionMethod.NumMatchFinderCyclesDefined)
- numProps--;
- CMyComPtr<ICompressSetCoderProperties> setCoderProperties;
- RINOK(deflateEncoder.QueryInterface(IID_ICompressSetCoderProperties, &setCoderProperties));
- RINOK(setCoderProperties->SetCoderProperties(propIDs, properties, numProps));
- }
- RINOK(deflateEncoder->Code(crcStream, outStream, NULL, NULL, progress));
-
- item.FileCRC = inStreamSpec->GetCRC();
- item.UnPackSize32 = (UInt32)inStreamSpec->GetSize();
- RINOK(outArchive.WritePostHeader(item));
- return updateCallback->SetOperationResult(NArchive::NUpdate::NOperationResult::kOK);
-}
-
-}}
diff --git a/CPP/7zip/Archive/GZip/GZipUpdate.h b/CPP/7zip/Archive/GZip/GZipUpdate.h
deleted file mode 100755
index 231d7972..00000000
--- a/CPP/7zip/Archive/GZip/GZipUpdate.h
+++ /dev/null
@@ -1,37 +0,0 @@
-// GZip/Update.h
-
-#ifndef __GZIP_UPDATE_H
-#define __GZIP_UPDATE_H
-
-#include "../IArchive.h"
-
-#include "../../Common/CreateCoder.h"
-
-#include "GZipOut.h"
-#include "GZipItem.h"
-
-namespace NArchive {
-namespace NGZip {
-
-struct CCompressionMethodMode
-{
- UInt32 NumPasses;
- UInt32 NumFastBytes;
- UInt32 Algo;
- bool NumMatchFinderCyclesDefined;
- UInt32 NumMatchFinderCycles;
-};
-
-HRESULT UpdateArchive(
- DECL_EXTERNAL_CODECS_LOC_VARS
- IInStream *inStream,
- UInt64 unpackSize,
- ISequentialOutStream *outStream,
- const CItem &newItem,
- const CCompressionMethodMode &compressionMethod,
- int indexInClient,
- IArchiveUpdateCallback *updateCallback);
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/GZip/StdAfx.h b/CPP/7zip/Archive/GZip/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/GZip/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/GzHandler.cpp b/CPP/7zip/Archive/GzHandler.cpp
new file mode 100755
index 00000000..8f91003f
--- /dev/null
+++ b/CPP/7zip/Archive/GzHandler.cpp
@@ -0,0 +1,820 @@
+// GzHandler.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/ComTry.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/PropVariant.h"
+#include "Windows/Time.h"
+
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+#include "../Compress/DeflateDecoder.h"
+#include "../Compress/DeflateEncoder.h"
+
+#include "Common/InStreamWithCRC.h"
+#include "Common/OutStreamWithCRC.h"
+#include "Common/ParseProperties.h"
+
+#define Get32(p) GetUi32(p)
+
+using namespace NWindows;
+
+namespace NArchive {
+namespace NGz {
+
+static const UInt16 kSignature = 0x8B1F;
+
+namespace NHeader
+{
+ namespace NFlags
+ {
+ const Byte kIsText = 1 << 0;
+ const Byte kCrc = 1 << 1;
+ const Byte kExtra = 1 << 2;
+ const Byte kName = 1 << 3;
+ const Byte kComment = 1 << 4;
+ }
+
+ namespace NExtraFlags
+ {
+ const Byte kMaximum = 2;
+ const Byte kFastest = 4;
+ }
+
+ namespace NCompressionMethod
+ {
+ const Byte kDeflate = 8;
+ }
+
+ namespace NHostOS
+ {
+ enum EEnum
+ {
+ kFAT = 0,
+ kAMIGA,
+ kVMS,
+ kUnix,
+ kVM_CMS,
+ kAtari,
+ kHPFS,
+ kMac,
+ kZ_System,
+ kCPM,
+ kTOPS20,
+ kNTFS,
+ kQDOS,
+ kAcorn,
+ kVFAT,
+ kMVS,
+ kBeOS,
+ kTandem,
+
+ kUnknown = 255
+ };
+ }
+}
+
+static const char *kHostOSes[] =
+{
+ "FAT",
+ "AMIGA",
+ "VMS",
+ "Unix",
+ "VM/CMS",
+ "Atari",
+ "HPFS",
+ "Macintosh",
+ "Z-System",
+ "CP/M",
+ "TOPS-20",
+ "NTFS",
+ "SMS/QDOS",
+ "Acorn",
+ "VFAT",
+ "MVS",
+ "BeOS",
+ "Tandem",
+ "OS/400",
+ "OS/X"
+};
+
+static const char *kUnknownOS = "Unknown";
+
+class CItem
+{
+ bool TestFlag(Byte flag) const { return (Flags & flag) != 0; }
+public:
+ Byte Method;
+ Byte Flags;
+ Byte ExtraFlags;
+ Byte HostOS;
+ UInt32 Time;
+ UInt32 Crc;
+ UInt32 Size32;
+
+ AString Name;
+ AString Comment;
+ // CByteBuffer Extra;
+
+ // bool IsText() const { return TestFlag(NHeader::NFlags::kIsText); }
+ bool HeaderCrcIsPresent() const { return TestFlag(NHeader::NFlags::kCrc); }
+ bool ExtraFieldIsPresent() const { return TestFlag(NHeader::NFlags::kExtra); }
+ bool NameIsPresent() const { return TestFlag(NHeader::NFlags::kName); }
+ bool CommentIsPresent() const { return TestFlag(NHeader::NFlags::kComment); }
+
+ void Clear()
+ {
+ Name.Empty();
+ Comment.Empty();
+ // Extra.SetCapacity(0);
+ }
+
+ HRESULT ReadHeader(NCompress::NDeflate::NDecoder::CCOMCoder *stream);
+ HRESULT ReadFooter1(NCompress::NDeflate::NDecoder::CCOMCoder *stream);
+ HRESULT ReadFooter2(ISequentialInStream *stream);
+
+ HRESULT WriteHeader(ISequentialOutStream *stream);
+ HRESULT WriteFooter(ISequentialOutStream *stream);
+};
+
+static HRESULT ReadBytes(NCompress::NDeflate::NDecoder::CCOMCoder *stream, Byte *data, UInt32 size)
+{
+ for (UInt32 i = 0; i < size; i++)
+ data[i] = stream->ReadByte();
+ return stream->InputEofError() ? S_FALSE : S_OK;
+}
+
+static HRESULT SkipBytes(NCompress::NDeflate::NDecoder::CCOMCoder *stream, UInt32 size)
+{
+ for (UInt32 i = 0; i < size; i++)
+ stream->ReadByte();
+ return stream->InputEofError() ? S_FALSE : S_OK;
+}
+
+static HRESULT ReadUInt16(NCompress::NDeflate::NDecoder::CCOMCoder *stream, UInt16 &value /* , UInt32 &crc */)
+{
+ value = 0;
+ for (int i = 0; i < 2; i++)
+ {
+ Byte b = stream->ReadByte();
+ if (stream->InputEofError())
+ return S_FALSE;
+ // crc = CRC_UPDATE_BYTE(crc, b);
+ value |= (UInt16(b) << (8 * i));
+ }
+ return S_OK;
+}
+
+static HRESULT ReadString(NCompress::NDeflate::NDecoder::CCOMCoder *stream, AString &s, UInt32 limit /* , UInt32 &crc */)
+{
+ s.Empty();
+ for (UInt32 i = 0; i < limit; i++)
+ {
+ Byte b = stream->ReadByte();
+ if (stream->InputEofError())
+ return S_FALSE;
+ // crc = CRC_UPDATE_BYTE(crc, b);
+ if (b == 0)
+ return S_OK;
+ s += (char)b;
+ }
+ return S_FALSE;
+}
+
+HRESULT CItem::ReadHeader(NCompress::NDeflate::NDecoder::CCOMCoder *stream)
+{
+ Clear();
+
+ // Header-CRC field had another meaning in old version of gzip!
+ // UInt32 crc = CRC_INIT_VAL;
+ Byte buf[10];
+
+ RINOK(ReadBytes(stream, buf, 10));
+
+ if (GetUi16(buf) != kSignature)
+ return S_FALSE;
+
+ Method = buf[2];
+
+ if (Method != NHeader::NCompressionMethod::kDeflate)
+ return S_FALSE;
+
+ Flags = buf[3];
+ Time = Get32(buf + 4);
+ ExtraFlags = buf[8];
+ HostOS = buf[9];
+
+ // crc = CrcUpdate(crc, buf, 10);
+
+ if (ExtraFieldIsPresent())
+ {
+ UInt16 extraSize;
+ RINOK(ReadUInt16(stream, extraSize /* , crc */));
+ RINOK(SkipBytes(stream, extraSize));
+ // Extra.SetCapacity(extraSize);
+ // RINOK(ReadStream_FALSE(stream, Extra, extraSize));
+ // crc = CrcUpdate(crc, Extra, extraSize);
+ }
+ if (NameIsPresent())
+ RINOK(ReadString(stream, Name, (1 << 10) /* , crc */));
+ if (CommentIsPresent())
+ RINOK(ReadString(stream, Comment, (1 << 16) /* , crc */));
+
+ if (HeaderCrcIsPresent())
+ {
+ UInt16 headerCRC;
+ // UInt32 dummy = 0;
+ RINOK(ReadUInt16(stream, headerCRC /* , dummy */));
+ /*
+ if ((UInt16)CRC_GET_DIGEST(crc) != headerCRC)
+ return S_FALSE;
+ */
+ }
+ return stream->InputEofError() ? S_FALSE : S_OK;
+}
+
+HRESULT CItem::ReadFooter1(NCompress::NDeflate::NDecoder::CCOMCoder *stream)
+{
+ Byte buf[8];
+ RINOK(ReadBytes(stream, buf, 8));
+ Crc = Get32(buf);
+ Size32 = Get32(buf + 4);
+ return stream->InputEofError() ? S_FALSE : S_OK;
+}
+
+HRESULT CItem::ReadFooter2(ISequentialInStream *stream)
+{
+ Byte buf[8];
+ RINOK(ReadStream_FALSE(stream, buf, 8));
+ Crc = Get32(buf);
+ Size32 = Get32(buf + 4);
+ return S_OK;
+}
+
+HRESULT CItem::WriteHeader(ISequentialOutStream *stream)
+{
+ Byte buf[10];
+ SetUi16(buf, kSignature);
+ buf[2] = Method;
+ buf[3] = Flags & NHeader::NFlags::kName;
+ // buf[3] |= NHeader::NFlags::kCrc;
+ SetUi32(buf + 4, Time);
+ buf[8] = ExtraFlags;
+ buf[9] = HostOS;
+ RINOK(WriteStream(stream, buf, 10));
+ // crc = CrcUpdate(CRC_INIT_VAL, buf, 10);
+ if (NameIsPresent())
+ {
+ // crc = CrcUpdate(crc, (const char *)Name, Name.Length() + 1);
+ RINOK(WriteStream(stream, (const char *)Name, Name.Length() + 1));
+ }
+ // SetUi16(buf, (UInt16)CRC_GET_DIGEST(crc));
+ // RINOK(WriteStream(stream, buf, 2));
+ return S_OK;
+}
+
+HRESULT CItem::WriteFooter(ISequentialOutStream *stream)
+{
+ Byte buf[8];
+ SetUi32(buf, Crc);
+ SetUi32(buf + 4, Size32);
+ return WriteStream(stream, buf, 8);
+}
+
+static const UInt32 kAlgoX1 = 0;
+static const UInt32 kAlgoX5 = 1;
+
+static const UInt32 kNumPassesX1 = 1;
+static const UInt32 kNumPassesX7 = 3;
+static const UInt32 kNumPassesX9 = 10;
+
+static const UInt32 kNumFastBytesX1 = 32;
+static const UInt32 kNumFastBytesX7 = 64;
+static const UInt32 kNumFastBytesX9 = 128;
+
+struct CCompressMode
+{
+ UInt32 NumPasses;
+ UInt32 NumFastBytes;
+ UInt32 Algo;
+ UInt32 Mc;
+ bool McDefined;
+
+ bool IsMaximum() const { return Algo > 0; }
+
+ void Init()
+ {
+ NumPasses = NumFastBytes = Mc = Algo = 0xFFFFFFFF;
+ McDefined = false;
+ }
+
+ void Normalize(UInt32 level)
+ {
+ if (level == 0xFFFFFFFF)
+ level = 5;
+ if (NumPasses == 0xFFFFFFFF)
+ NumPasses =
+ (level >= 9 ? kNumPassesX9 :
+ (level >= 7 ? kNumPassesX7 :
+ kNumPassesX1));
+ if (NumFastBytes == 0xFFFFFFFF)
+ NumFastBytes =
+ (level >= 9 ? kNumFastBytesX9 :
+ (level >= 7 ? kNumFastBytesX7 :
+ kNumFastBytesX1));
+ if (Algo == 0xFFFFFFFF)
+ Algo = (level >= 5 ?
+ kAlgoX5 :
+ kAlgoX1);
+ }
+};
+
+class CHandler:
+ public IInArchive,
+ public IArchiveOpenSeq,
+ public IOutArchive,
+ public ISetProperties,
+ public CMyUnknownImp
+{
+ CItem _item;
+ UInt64 _startPosition;
+ UInt64 _headerSize;
+ UInt64 _packSize;
+ bool _packSizeDefined;
+ CMyComPtr<IInStream> _stream;
+ CMyComPtr<ICompressCoder> _decoder;
+ NCompress::NDeflate::NDecoder::CCOMCoder *_decoderSpec;
+
+ CCompressMode _method;
+ UInt32 _level;
+
+ void InitMethodProperties()
+ {
+ _level = 0xFFFFFFFF;
+ _method.Init();
+ }
+
+public:
+ MY_UNKNOWN_IMP4(IInArchive, IArchiveOpenSeq, IOutArchive, ISetProperties)
+ INTERFACE_IInArchive(;)
+ INTERFACE_IOutArchive(;)
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream);
+ STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProps);
+
+ CHandler()
+ {
+ InitMethodProperties();
+ _decoderSpec = new NCompress::NDeflate::NDecoder::CCOMCoder;
+ _decoder = _decoderSpec;
+ }
+};
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidHostOS, VT_BSTR},
+ { NULL, kpidCRC, VT_UI4}
+ // { NULL, kpidComment, VT_BSTR}
+}
+;
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPhySize: if (_packSizeDefined) prop = _packSize; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = 1;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPath:
+ if (_item.NameIsPresent())
+ prop = MultiByteToUnicodeString(_item.Name, CP_ACP);
+ break;
+ // case kpidComment: if (_item.CommentIsPresent()) prop = MultiByteToUnicodeString(_item.Comment, CP_ACP); break;
+ case kpidMTime:
+ {
+ if (_item.Time != 0)
+ {
+ FILETIME utc;
+ NTime::UnixTimeToFileTime(_item.Time, utc);
+ prop = utc;
+ }
+ break;
+ }
+ case kpidSize: if (_stream) prop = (UInt64)_item.Size32; break;
+ case kpidPackSize: if (_packSizeDefined) prop = _packSize; break;
+ case kpidHostOS: prop = (_item.HostOS < sizeof(kHostOSes) / sizeof(kHostOSes[0])) ?
+ kHostOSes[_item.HostOS] : kUnknownOS; break;
+ case kpidCRC: if (_stream) prop = _item.Crc; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream, const UInt64 *, IArchiveOpenCallback *)
+{
+ COM_TRY_BEGIN
+ HRESULT res;
+ try
+ {
+ RINOK(stream->Seek(0, STREAM_SEEK_CUR, &_startPosition));
+ res = OpenSeq(stream);
+ if (res == S_OK)
+ {
+ UInt64 endPos;
+ res = stream->Seek(-8, STREAM_SEEK_END, &endPos);
+ _packSize = endPos + 8 - _startPosition;
+ _packSizeDefined = true;
+ if (res == S_OK)
+ {
+ res = _item.ReadFooter2(stream);
+ _stream = stream;
+ }
+ }
+ }
+ catch(...) { res = S_FALSE; }
+ if (res != S_OK)
+ Close();
+ return res;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::OpenSeq(ISequentialInStream *stream)
+{
+ COM_TRY_BEGIN
+ HRESULT res;
+ try
+ {
+ Close();
+ _decoderSpec->SetInStream(stream);
+ _decoderSpec->InitInStream(true);
+ res = _item.ReadHeader(_decoderSpec);
+ _headerSize = _decoderSpec->GetInputProcessedSize();
+ }
+ catch(...) { res = S_FALSE; }
+ if (res != S_OK)
+ Close();
+ return res;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _packSizeDefined = false;
+ _stream.Release();
+ _decoderSpec->ReleaseInStream();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool allFilesMode = (numItems == (UInt32)-1);
+ if (!allFilesMode)
+ {
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
+ }
+
+ bool testMode = (_aTestMode != 0);
+ if (_stream)
+ extractCallback->SetTotal(_packSize);
+ UInt64 currentTotalPacked = 0;
+ RINOK(extractCallback->SetCompleted(&currentTotalPacked));
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
+ if (!testMode && !realOutStream)
+ return S_OK;
+
+ extractCallback->PrepareOperation(askMode);
+
+ COutStreamWithCRC *outStreamSpec = new COutStreamWithCRC;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+ outStreamSpec->SetStream(realOutStream);
+ outStreamSpec->Init();
+ realOutStream.Release();
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, true);
+
+ if (_stream)
+ {
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ _decoderSpec->InitInStream(true);
+ }
+ bool firstItem = true;
+ Int32 opRes;
+ for (;;)
+ {
+ lps->InSize = _packSize = _decoderSpec->GetInputProcessedSize();
+ _packSizeDefined = true;
+ lps->OutSize = outStreamSpec->GetSize();
+ RINOK(lps->SetCur());
+
+ CItem item;
+ if (!firstItem || _stream)
+ {
+ HRESULT result = item.ReadHeader(_decoderSpec);
+ if (result != S_OK)
+ {
+ if (result != S_FALSE)
+ return result;
+ opRes = firstItem ?
+ NArchive::NExtract::NOperationResult::kDataError :
+ NArchive::NExtract::NOperationResult::kOK;
+ break;
+ }
+ }
+ firstItem = false;
+
+ UInt64 startOffset = outStreamSpec->GetSize();
+ outStreamSpec->InitCRC();
+
+ HRESULT result = _decoderSpec->CodeResume(outStream, NULL, progress);
+ if (result != S_OK)
+ {
+ if (result != S_FALSE)
+ return result;
+ opRes = NArchive::NExtract::NOperationResult::kDataError;
+ break;
+ }
+
+ _decoderSpec->AlignToByte();
+ if (item.ReadFooter1(_decoderSpec) != S_OK)
+ {
+ opRes = NArchive::NExtract::NOperationResult::kDataError;
+ break;
+ }
+ if (item.Crc != outStreamSpec->GetCRC() ||
+ item.Size32 != (UInt32)(outStreamSpec->GetSize() - startOffset))
+ {
+ opRes = NArchive::NExtract::NOperationResult::kCRCError;
+ break;
+ }
+ }
+ outStream.Release();
+ return extractCallback->SetOperationResult(opRes);
+ COM_TRY_END
+}
+
+static const Byte kHostOS =
+ #ifdef _WIN32
+ NHeader::NHostOS::kFAT;
+ #else
+ NHeader::NHostOS::kUnix;
+ #endif
+
+static HRESULT UpdateArchive(
+ ISequentialOutStream *outStream,
+ UInt64 unpackSize,
+ const CItem &newItem,
+ const CCompressMode &compressionMode,
+ IArchiveUpdateCallback *updateCallback)
+{
+ UInt64 complexity = 0;
+ RINOK(updateCallback->SetTotal(unpackSize));
+ RINOK(updateCallback->SetCompleted(&complexity));
+
+ CMyComPtr<ISequentialInStream> fileInStream;
+
+ RINOK(updateCallback->GetStream(0, &fileInStream));
+
+ CSequentialInStreamWithCRC *inStreamSpec = new CSequentialInStreamWithCRC;
+ CMyComPtr<ISequentialInStream> crcStream(inStreamSpec);
+ inStreamSpec->SetStream(fileInStream);
+ inStreamSpec->Init();
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(updateCallback, true);
+
+ CItem item = newItem;
+ item.Method = NHeader::NCompressionMethod::kDeflate;
+ item.ExtraFlags = compressionMode.IsMaximum() ?
+ NHeader::NExtraFlags::kMaximum :
+ NHeader::NExtraFlags::kFastest;
+
+ item.HostOS = kHostOS;
+
+ RINOK(item.WriteHeader(outStream));
+
+ NCompress::NDeflate::NEncoder::CCOMCoder *deflateEncoderSpec = new NCompress::NDeflate::NEncoder::CCOMCoder;
+ CMyComPtr<ICompressCoder> deflateEncoder = deflateEncoderSpec;
+ {
+ NWindows::NCOM::CPropVariant props[] =
+ {
+ compressionMode.Algo,
+ compressionMode.NumPasses,
+ compressionMode.NumFastBytes,
+ compressionMode.Mc
+ };
+ PROPID propIDs[] =
+ {
+ NCoderPropID::kAlgorithm,
+ NCoderPropID::kNumPasses,
+ NCoderPropID::kNumFastBytes,
+ NCoderPropID::kMatchFinderCycles
+ };
+ int numProps = sizeof(propIDs) / sizeof(propIDs[0]);
+ if (!compressionMode.McDefined)
+ numProps--;
+ RINOK(deflateEncoderSpec->SetCoderProperties(propIDs, props, numProps));
+ }
+ RINOK(deflateEncoder->Code(crcStream, outStream, NULL, NULL, progress));
+
+ item.Crc = inStreamSpec->GetCRC();
+ item.Size32 = (UInt32)inStreamSpec->GetSize();
+ RINOK(item.WriteFooter(outStream));
+ return updateCallback->SetOperationResult(NArchive::NUpdate::NOperationResult::kOK);
+}
+
+STDMETHODIMP CHandler::GetFileTimeType(UInt32 *timeType)
+{
+ *timeType = NFileTimeType::kUnix;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
+ IArchiveUpdateCallback *updateCallback)
+{
+ if (numItems != 1)
+ return E_INVALIDARG;
+
+ Int32 newData, newProps;
+ UInt32 indexInArchive;
+ if (!updateCallback)
+ return E_FAIL;
+ RINOK(updateCallback->GetUpdateItemInfo(0, &newData, &newProps, &indexInArchive));
+
+ CItem newItem = _item;
+ newItem.ExtraFlags = 0;
+ newItem.Flags = 0;
+ if (IntToBool(newProps))
+ {
+ {
+ FILETIME utcTime;
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidMTime, &prop));
+ if (prop.vt != VT_FILETIME)
+ return E_INVALIDARG;
+ utcTime = prop.filetime;
+ if (!NTime::FileTimeToUnixTime(utcTime, newItem.Time))
+ return E_INVALIDARG;
+ }
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidPath, &prop));
+ if (prop.vt == VT_BSTR)
+ {
+ UString name = prop.bstrVal;
+ int dirDelimiterPos = name.ReverseFind(CHAR_PATH_SEPARATOR);
+ if (dirDelimiterPos >= 0)
+ name = name.Mid(dirDelimiterPos + 1);
+ newItem.Name = UnicodeStringToMultiByte(name, CP_ACP);
+ if (!newItem.Name.IsEmpty())
+ newItem.Flags |= NHeader::NFlags::kName;
+ }
+ else if (prop.vt != VT_EMPTY)
+ return E_INVALIDARG;
+ }
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidIsDir, &prop));
+ if (prop.vt == VT_BOOL)
+ {
+ if (prop.boolVal != VARIANT_FALSE)
+ return E_INVALIDARG;
+ }
+ else if (prop.vt != VT_EMPTY)
+ return E_INVALIDARG;
+ }
+ }
+
+ if (IntToBool(newData))
+ {
+ UInt64 size;
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidSize, &prop));
+ if (prop.vt != VT_UI8)
+ return E_INVALIDARG;
+ size = prop.uhVal.QuadPart;
+ }
+
+ _method.Normalize(_level);
+ return UpdateArchive(outStream, size, newItem, _method, updateCallback);
+ }
+
+ if (indexInArchive != 0)
+ return E_INVALIDARG;
+
+ if (!_stream)
+ return E_NOTIMPL;
+
+ UInt64 offset = _startPosition;
+ if (IntToBool(newProps))
+ {
+ newItem.WriteHeader(outStream);
+ offset += _headerSize;
+ }
+ RINOK(_stream->Seek(offset, STREAM_SEEK_SET, NULL));
+ return NCompress::CopyStream(_stream, outStream, NULL);
+}
+
+STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProps)
+{
+ InitMethodProperties();
+ for (int i = 0; i < numProps; i++)
+ {
+ UString name = names[i];
+ name.MakeUpper();
+ if (name.IsEmpty())
+ return E_INVALIDARG;
+ const PROPVARIANT &prop = values[i];
+ if (name[0] == L'X')
+ {
+ UInt32 level = 9;
+ RINOK(ParsePropValue(name.Mid(1), prop, level));
+ _level = level;
+ }
+ else if (name.Left(4) == L"PASS")
+ {
+ UInt32 num = kNumPassesX9;
+ RINOK(ParsePropValue(name.Mid(4), prop, num));
+ _method.NumPasses = num;
+ }
+ else if (name.Left(2) == L"FB")
+ {
+ UInt32 num = kNumFastBytesX9;
+ RINOK(ParsePropValue(name.Mid(2), prop, num));
+ _method.NumFastBytes = num;
+ }
+ else if (name.Left(2) == L"MC")
+ {
+ UInt32 num = 0xFFFFFFFF;
+ RINOK(ParsePropValue(name.Mid(2), prop, num));
+ _method.Mc = num;
+ _method.McDefined = true;
+ }
+ else if (name.Left(1) == L"A")
+ {
+ UInt32 num = kAlgoX5;
+ RINOK(ParsePropValue(name.Mid(1), prop, num));
+ _method.Algo = num;
+ }
+ else
+ return E_INVALIDARG;
+ }
+ return S_OK;
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+#ifndef EXTRACT_ONLY
+static IOutArchive *CreateArcOut() { return new CHandler; }
+#else
+#define CreateArcOut 0
+#endif
+
+static CArcInfo g_ArcInfo =
+ { L"GZip", L"gz gzip tgz tpz", L"* * .tar .tar", 0xEF, { 0x1F, 0x8B, 8 }, 3, true, CreateArc, CreateArcOut };
+
+REGISTER_ARC(GZip)
+
+}}
diff --git a/CPP/7zip/Archive/IArchive.h b/CPP/7zip/Archive/IArchive.h
index 88d6c408..85320276 100755
--- a/CPP/7zip/Archive/IArchive.h
+++ b/CPP/7zip/Archive/IArchive.h
@@ -3,8 +3,8 @@
#ifndef __IARCHIVE_H
#define __IARCHIVE_H
-#include "../IStream.h"
#include "../IProgress.h"
+#include "../IStream.h"
#include "../PropID.h"
#define ARCHIVE_INTERFACE_SUB(i, base, x) DECL_INTERFACE_SUB(i, base, 6, x)
@@ -82,7 +82,6 @@ ARCHIVE_INTERFACE(IArchiveOpenCallback, 0x10)
#define INTERFACE_IArchiveExtractCallback(x) \
INTERFACE_IProgress(x) \
- /* GetStream OUT: S_OK - OK, S_FALSE - skeep this file */ \
STDMETHOD(GetStream)(UInt32 index, ISequentialOutStream **outStream, Int32 askExtractMode) x; \
STDMETHOD(PrepareOperation)(Int32 askExtractMode) x; \
STDMETHOD(SetOperationResult)(Int32 resultEOperationResult) x; \
@@ -139,6 +138,10 @@ ARCHIVE_INTERFACE(IInArchive, 0x60)
INTERFACE_IInArchive(PURE)
};
+ARCHIVE_INTERFACE(IArchiveOpenSeq, 0x61)
+{
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream) PURE;
+};
#define INTERFACE_IArchiveUpdateCallback(x) \
INTERFACE_IProgress(x); \
@@ -217,11 +220,14 @@ ARCHIVE_INTERFACE(ISetProperties, 0x03)
{ *numProperties = sizeof(kArcProps) / sizeof(kArcProps[0]); return S_OK; } \
STDMETHODIMP CHandler::GetArchivePropertyInfo IMP_IInArchive_GetProp_WITH_NAME(kArcProps)
-#define IMP_IInArchive_ArcProps_NO \
+#define IMP_IInArchive_ArcProps_NO_Table \
STDMETHODIMP CHandler::GetNumberOfArchiveProperties(UInt32 *numProperties) \
{ *numProperties = 0; return S_OK; } \
STDMETHODIMP CHandler::GetArchivePropertyInfo(UInt32, BSTR *, PROPID *, VARTYPE *) \
{ return E_NOTIMPL; } \
+
+#define IMP_IInArchive_ArcProps_NO \
+ IMP_IInArchive_ArcProps_NO_Table \
STDMETHODIMP CHandler::GetArchiveProperty(PROPID, PROPVARIANT *value) \
{ value->vt = VT_EMPTY; return S_OK; }
diff --git a/CPP/7zip/Archive/Icons/fat.ico b/CPP/7zip/Archive/Icons/fat.ico
new file mode 100755
index 00000000..882753ac
--- /dev/null
+++ b/CPP/7zip/Archive/Icons/fat.ico
Binary files differ
diff --git a/CPP/7zip/Archive/Icons/ntfs.ico b/CPP/7zip/Archive/Icons/ntfs.ico
new file mode 100755
index 00000000..6b2aeb00
--- /dev/null
+++ b/CPP/7zip/Archive/Icons/ntfs.ico
Binary files differ
diff --git a/CPP/7zip/Archive/Icons/vhd.ico b/CPP/7zip/Archive/Icons/vhd.ico
new file mode 100755
index 00000000..33bed3c9
--- /dev/null
+++ b/CPP/7zip/Archive/Icons/vhd.ico
Binary files differ
diff --git a/CPP/7zip/Archive/Icons/xar.ico b/CPP/7zip/Archive/Icons/xar.ico
index 02707351..281aa7dc 100755
--- a/CPP/7zip/Archive/Icons/xar.ico
+++ b/CPP/7zip/Archive/Icons/xar.ico
Binary files differ
diff --git a/CPP/7zip/Archive/Icons/xz.ico b/CPP/7zip/Archive/Icons/xz.ico
new file mode 100755
index 00000000..02707351
--- /dev/null
+++ b/CPP/7zip/Archive/Icons/xz.ico
Binary files differ
diff --git a/CPP/7zip/Archive/Iso/IsoHandler.cpp b/CPP/7zip/Archive/Iso/IsoHandler.cpp
index f0c926c4..ed8da189 100755
--- a/CPP/7zip/Archive/Iso/IsoHandler.cpp
+++ b/CPP/7zip/Archive/Iso/IsoHandler.cpp
@@ -46,9 +46,9 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
Close();
// try
{
- if(_archive.Open(stream) != S_OK)
+ if (_archive.Open(stream) != S_OK)
return S_FALSE;
- _inStream = stream;
+ _stream = stream;
}
// catch(...) { return S_FALSE; }
return S_OK;
@@ -58,7 +58,7 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
STDMETHODIMP CHandler::Close()
{
_archive.Clear();
- _inStream.Release();
+ _stream.Release();
return S_OK;
}
@@ -160,7 +160,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
bool allFilesMode = (numItems == UInt32(-1));
if (allFilesMode)
numItems = _archive.Refs.Size();
- if(numItems == 0)
+ if (numItems == 0)
return S_OK;
UInt64 totalSize = 0;
UInt32 i;
@@ -192,7 +192,10 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_inStream);
+ streamSpec->SetStream(_stream);
+
+ CLimitedSequentialOutStream *outStreamSpec = new CLimitedSequentialOutStream;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
{
@@ -211,7 +214,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
{
const CRef &ref = _archive.Refs[index];
const CDir &item = ref.Dir->_subItems[ref.Index];
- if(item.IsDir())
+ if (item.IsDir())
{
RINOK(extractCallback->PrepareOperation(askMode));
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
@@ -231,16 +234,14 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
if (!testMode && (!realOutStream))
continue;
RINOK(extractCallback->PrepareOperation(askMode));
- if (testMode)
- {
- RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
- continue;
- }
- RINOK(_inStream->Seek(blockIndex * _archive.BlockSize, STREAM_SEEK_SET, NULL));
- streamSpec->Init(currentItemSize);
- RINOK(copyCoder->Code(inStream, realOutStream, NULL, NULL, progress));
+ outStreamSpec->SetStream(realOutStream);
realOutStream.Release();
- RINOK(extractCallback->SetOperationResult((copyCoderSpec->TotalSize == currentItemSize) ?
+ outStreamSpec->Init(currentItemSize);
+ RINOK(_stream->Seek(blockIndex * _archive.BlockSize, STREAM_SEEK_SET, NULL));
+ streamSpec->Init(currentItemSize);
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ outStreamSpec->ReleaseStream();
+ RINOK(extractCallback->SetOperationResult(outStreamSpec->IsFinishedOK() ?
NArchive::NExtract::NOperationResult::kOK:
NArchive::NExtract::NOperationResult::kDataError));
}
@@ -248,4 +249,30 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
COM_TRY_END
}
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ *stream = 0;
+ UInt64 blockIndex;
+ UInt64 currentItemSize;
+ if (index < (UInt32)_archive.Refs.Size())
+ {
+ const CRef &ref = _archive.Refs[index];
+ const CDir &item = ref.Dir->_subItems[ref.Index];
+ if (item.IsDir())
+ return S_FALSE;
+ currentItemSize = item.DataLength;
+ blockIndex = item.ExtentLocation;
+ }
+ else
+ {
+ int bootIndex = index - _archive.Refs.Size();
+ const CBootInitialEntry &be = _archive.BootEntries[bootIndex];
+ currentItemSize = _archive.GetBootItemSize(bootIndex);
+ blockIndex = be.LoadRBA;
+ }
+ return CreateLimitedInStream(_stream, blockIndex * _archive.BlockSize, currentItemSize, stream);
+ COM_TRY_END
+}
+
}}
diff --git a/CPP/7zip/Archive/Iso/IsoHandler.h b/CPP/7zip/Archive/Iso/IsoHandler.h
index bb905a22..1dcade8f 100755
--- a/CPP/7zip/Archive/Iso/IsoHandler.h
+++ b/CPP/7zip/Archive/Iso/IsoHandler.h
@@ -1,4 +1,4 @@
-// Iso/Handler.h
+// IsoHandler.h
#ifndef __ISO_HANDLER_H
#define __ISO_HANDLER_H
@@ -6,26 +6,23 @@
#include "Common/MyCom.h"
#include "../IArchive.h"
-#include "IsoItem.h"
#include "IsoIn.h"
+#include "IsoItem.h"
namespace NArchive {
namespace NIso {
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
+ CMyComPtr<IInStream> _stream;
+ CInArchive _archive;
public:
- MY_UNKNOWN_IMP1(
- IInArchive
- )
-
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
INTERFACE_IInArchive(;)
-
-private:
- CMyComPtr<IInStream> _inStream;
- CInArchive _archive;
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
}}
diff --git a/CPP/7zip/Archive/Iso/IsoIn.cpp b/CPP/7zip/Archive/Iso/IsoIn.cpp
index dee23395..84143348 100755
--- a/CPP/7zip/Archive/Iso/IsoIn.cpp
+++ b/CPP/7zip/Archive/Iso/IsoIn.cpp
@@ -3,9 +3,6 @@
#include "StdAfx.h"
#include "IsoIn.h"
-#include "IsoHeader.h"
-
-#include "Windows/Defs.h"
#include "../../Common/StreamUtils.h"
@@ -35,13 +32,13 @@ void CInArchive::ReadBytes(Byte *data, UInt32 size)
data[i] = ReadByte();
}
-void CInArchive::Skeep(size_t size)
+void CInArchive::Skip(size_t size)
{
while (size-- != 0)
ReadByte();
}
-void CInArchive::SkeepZeros(size_t size)
+void CInArchive::SkipZeros(size_t size)
{
while (size-- != 0)
{
@@ -174,8 +171,8 @@ void CInArchive::ReadDirRecord2(CDirRecord &r, Byte len)
ReadBytes((Byte *)r.FileId, idLen);
int padSize = 1 - (idLen & 1);
- // SkeepZeros(1 - (idLen & 1));
- Skeep(1 - (idLen & 1)); // it's bug in some cd's. Must be zeros
+ // SkipZeros(1 - (idLen & 1));
+ Skip(1 - (idLen & 1)); // it's bug in some cd's. Must be zeros
int curPos = 33 + idLen + padSize;
if (curPos > len)
@@ -199,7 +196,7 @@ void CInArchive::ReadVolumeDescriptor(CVolumeDescriptor &d)
d.VolFlags = ReadByte();
ReadBytes(d.SystemId, sizeof(d.SystemId));
ReadBytes(d.VolumeId, sizeof(d.VolumeId));
- SkeepZeros(8);
+ SkipZeros(8);
d.VolumeSpaceSize = ReadUInt32();
ReadBytes(d.EscapeSequence, sizeof(d.EscapeSequence));
d.VolumeSetSize = ReadUInt16();
@@ -223,9 +220,9 @@ void CInArchive::ReadVolumeDescriptor(CVolumeDescriptor &d)
ReadDateTime(d.ExpirationTime);
ReadDateTime(d.EffectiveTime);
d.FileStructureVersion = ReadByte(); // = 1
- SkeepZeros(1);
+ SkipZeros(1);
ReadBytes(d.ApplicationUse, sizeof(d.ApplicationUse));
- SkeepZeros(653);
+ SkipZeros(653);
}
static const Byte kSig_CD001[5] = { 'C', 'D', '0', '0', '1' };
@@ -371,7 +368,7 @@ HRESULT CInArchive::Open2()
}
else
break;
- SkeepZeros(0x800 - 7);
+ SkipZeros(0x800 - 7);
continue;
*/
}
@@ -382,7 +379,7 @@ HRESULT CInArchive::Open2()
if (sig[0] == NVolDescType::kTerminator)
{
break;
- // Skeep(0x800 - 7);
+ // Skip(0x800 - 7);
// continue;
}
switch(sig[0])
diff --git a/CPP/7zip/Archive/Iso/IsoIn.h b/CPP/7zip/Archive/Iso/IsoIn.h
index ce53a1e3..49687e27 100755
--- a/CPP/7zip/Archive/Iso/IsoIn.h
+++ b/CPP/7zip/Archive/Iso/IsoIn.h
@@ -3,13 +3,13 @@
#ifndef __ARCHIVE_ISO_IN_H
#define __ARCHIVE_ISO_IN_H
-#include "Common/MyCom.h"
#include "Common/IntToString.h"
+#include "Common/MyCom.h"
#include "../../IStream.h"
-#include "IsoItem.h"
#include "IsoHeader.h"
+#include "IsoItem.h"
namespace NArchive {
namespace NIso {
@@ -159,8 +159,8 @@ struct CBootInitialEntry
s += L"_";
if (BootMediaType >= kNumBootMediaTypes)
{
- wchar_t name[32];
- ConvertUInt64ToString(BootMediaType, name);
+ wchar_t name[16];
+ ConvertUInt32ToString(BootMediaType, name);
s += name;
}
else
@@ -232,8 +232,8 @@ class CInArchive
bool _bootIsDefined;
CBootRecordDescriptor _bootDesc;
- void Skeep(size_t size);
- void SkeepZeros(size_t size);
+ void Skip(size_t size);
+ void SkipZeros(size_t size);
Byte ReadByte();
void ReadBytes(Byte *data, UInt32 size);
UInt16 ReadUInt16Spec();
diff --git a/CPP/7zip/Archive/Lzh/LzhCRC.cpp b/CPP/7zip/Archive/Lzh/LzhCRC.cpp
deleted file mode 100755
index e299bf6c..00000000
--- a/CPP/7zip/Archive/Lzh/LzhCRC.cpp
+++ /dev/null
@@ -1,43 +0,0 @@
-// LzhCRC.cpp
-
-#include "StdAfx.h"
-
-#include "LzhCRC.h"
-
-namespace NArchive {
-namespace NLzh {
-
-static const UInt16 kCRCPoly = 0xA001;
-
-UInt16 CCRC::Table[256];
-
-void CCRC::InitTable()
-{
- for (UInt32 i = 0; i < 256; i++)
- {
- UInt32 r = i;
- for (int j = 0; j < 8; j++)
- if (r & 1)
- r = (r >> 1) ^ kCRCPoly;
- else
- r >>= 1;
- CCRC::Table[i] = (UInt16)r;
- }
-}
-
-class CCRCTableInit
-{
-public:
- CCRCTableInit() { CCRC::InitTable(); }
-} g_CRCTableInit;
-
-void CCRC::Update(const void *data, size_t size)
-{
- UInt16 v = _value;
- const Byte *p = (const Byte *)data;
- for (; size > 0; size--, p++)
- v = (UInt16)(Table[((Byte)(v)) ^ *p] ^ (v >> 8));
- _value = v;
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzh/LzhCRC.h b/CPP/7zip/Archive/Lzh/LzhCRC.h
deleted file mode 100755
index be2a4569..00000000
--- a/CPP/7zip/Archive/Lzh/LzhCRC.h
+++ /dev/null
@@ -1,27 +0,0 @@
-// LzhCRC.h
-
-#ifndef __LZH_CRC_H
-#define __LZH_CRC_H
-
-#include <stddef.h>
-#include "Common/Types.h"
-
-namespace NArchive {
-namespace NLzh {
-
-class CCRC
-{
- UInt16 _value;
-public:
- static UInt16 Table[256];
- static void InitTable();
-
- CCRC(): _value(0){};
- void Init() { _value = 0; }
- void Update(const void *data, size_t size);
- UInt16 GetDigest() const { return _value; }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhHandler.cpp b/CPP/7zip/Archive/Lzh/LzhHandler.cpp
deleted file mode 100755
index 66153f7a..00000000
--- a/CPP/7zip/Archive/Lzh/LzhHandler.cpp
+++ /dev/null
@@ -1,387 +0,0 @@
-// LzhHandler.cpp
-
-#include "StdAfx.h"
-
-#include "Common/ComTry.h"
-#include "Common/Defs.h"
-#include "Common/StringConvert.h"
-
-#include "Windows/PropVariant.h"
-#include "Windows/Time.h"
-
-#include "LzhHandler.h"
-#include "LzhOutStreamWithCRC.h"
-
-#include "../../ICoder.h"
-
-#include "../../Common/LimitedStreams.h"
-#include "../../Common/ProgressUtils.h"
-
-#include "../../Compress/CopyCoder.h"
-#include "../../Compress/LzhDecoder.h"
-
-#include "../Common/ItemNameUtils.h"
-
-using namespace NWindows;
-using namespace NTime;
-
-namespace NArchive {
-namespace NLzh{
-
-struct COsPair
-{
- Byte Id;
- const wchar_t *Name;
-};
-
-COsPair g_OsPairs[] =
-{
- { 'M', L"MS-DOS" },
- { '2', L"OS/2" },
- { '9', L"OS9" },
- { 'K', L"OS/68K" },
- { '3', L"OS/386" },
- { 'H', L"HUMAN" },
- { 'U', L"UNIX" },
- { 'C', L"CP/M" },
- { 'F', L"FLEX" },
- { 'm', L"Mac" },
- { 'R', L"Runser" },
- { 'T', L"TownsOS" },
- { 'X', L"XOSK" },
- { 'w', L"Windows95" },
- { 'W', L"WindowsNT" },
- { 0, L"MS-DOS" },
- { 'J', L"Java VM" }
-};
-
-const wchar_t *kUnknownOS = L"Unknown";
-
-const int kNumHostOSes = sizeof(g_OsPairs) / sizeof(g_OsPairs[0]);
-
-static const wchar_t *GetOS(Byte osId)
-{
- for (int i = 0; i < kNumHostOSes; i++)
- if (g_OsPairs[i].Id == osId)
- return g_OsPairs[i].Name;
- return kUnknownOS;
-};
-
-STATPROPSTG kProps[] =
-{
- { NULL, kpidPath, VT_BSTR},
- { NULL, kpidIsDir, VT_BOOL},
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
- { NULL, kpidMTime, VT_FILETIME},
- { NULL, kpidAttrib, VT_UI4},
-
- // { NULL, kpidCommented, VT_BOOL},
-
- { NULL, kpidCRC, VT_UI4},
-
- { NULL, kpidMethod, VT_UI1},
- { NULL, kpidHostOS, VT_BSTR}
-
-};
-
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
-
-CHandler::CHandler() {}
-
-STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
-{
- *numItems = _items.Size();
- return S_OK;
-}
-
-STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
-{
- COM_TRY_BEGIN
- NWindows::NCOM::CPropVariant prop;
- const CItemEx &item = _items[index];
- switch(propID)
- {
- case kpidPath:
- {
- UString s = NItemName::WinNameToOSName(MultiByteToUnicodeString(item.GetName(), CP_OEMCP));
- if (!s.IsEmpty())
- {
- if (s[s.Length() - 1] == WCHAR_PATH_SEPARATOR)
- s.Delete(s.Length() - 1);
- prop = s;
- }
- break;
- }
- case kpidIsDir: prop = item.IsDir(); break;
- case kpidSize: prop = item.Size; break;
- case kpidPackSize: prop = item.PackSize; break;
- case kpidCRC: prop = (UInt32)item.CRC; break;
- case kpidHostOS: prop = GetOS(item.OsId); break;
- case kpidMTime:
- {
- FILETIME utcFileTime;
- UInt32 unixTime;
- if (item.GetUnixTime(unixTime))
- NTime::UnixTimeToFileTime(unixTime, utcFileTime);
- else
- {
- FILETIME localFileTime;
- if (DosTimeToFileTime(item.ModifiedTime, localFileTime))
- {
- if (!LocalFileTimeToFileTime(&localFileTime, &utcFileTime))
- utcFileTime.dwHighDateTime = utcFileTime.dwLowDateTime = 0;
- }
- else
- utcFileTime.dwHighDateTime = utcFileTime.dwLowDateTime = 0;
- }
- prop = utcFileTime;
- break;
- }
- /*
- case kpidAttrib: prop = (UInt32)item.Attributes; break;
- case kpidCommented: prop = item.IsCommented(); break;
- */
- case kpidMethod:
- {
- wchar_t method2[kMethodIdSize + 1];
- method2[kMethodIdSize] = 0;
- for (int i = 0; i < kMethodIdSize; i++)
- method2[i] = item.Method[i];
- prop = method2;
- break;
- }
- }
- prop.Detach(value);
- return S_OK;
- COM_TRY_END
-}
-
-/*
-class CProgressImp: public CProgressVirt
-{
-public:
- CMyComPtr<IArchiveOpenCallback> Callback;
- STDMETHOD(SetCompleted)(const UInt64 *numFiles);
-};
-
-STDMETHODIMP CProgressImp::SetCompleted(const UInt64 *numFiles)
-{
- if (Callback)
- return Callback->SetCompleted(numFiles, NULL);
- return S_OK;
-}
-*/
-
-STDMETHODIMP CHandler::Open(IInStream *stream,
- const UInt64 * /* maxCheckStartPosition */, IArchiveOpenCallback *callback)
-{
- COM_TRY_BEGIN
- try
- {
- _items.Clear();
- CInArchive archive;
-
- UInt64 endPos = 0;
- bool needSetTotal = true;
-
- if (callback != NULL)
- {
- RINOK(stream->Seek(0, STREAM_SEEK_END, &endPos));
- RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
- }
-
- RINOK(archive.Open(stream));
- for (;;)
- {
- CItemEx item;
- bool filled;
- HRESULT result = archive.GetNextItem(filled, item);
- if (result == S_FALSE)
- return S_FALSE;
- if (result != S_OK)
- return S_FALSE;
- if (!filled)
- break;
- _items.Add(item);
- archive.Skeep(item.PackSize);
- if (callback != NULL)
- {
- if (needSetTotal)
- {
- RINOK(callback->SetTotal(NULL, &endPos));
- needSetTotal = false;
- }
- if (_items.Size() % 100 == 0)
- {
- UInt64 numFiles = _items.Size();
- UInt64 numBytes = item.DataPosition;
- RINOK(callback->SetCompleted(&numFiles, &numBytes));
- }
- }
- }
- if (_items.IsEmpty())
- return S_FALSE;
-
- _stream = stream;
- }
- catch(...)
- {
- return S_FALSE;
- }
- COM_TRY_END
- return S_OK;
-}
-
-STDMETHODIMP CHandler::Close()
-{
- _items.Clear();
- _stream.Release();
- return S_OK;
-}
-
-
-
-//////////////////////////////////////
-// CHandler::DecompressItems
-
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 testModeSpec, IArchiveExtractCallback *extractCallback)
-{
- COM_TRY_BEGIN
- bool testMode = (testModeSpec != 0);
- UInt64 totalUnPacked = 0, totalPacked = 0;
- bool allFilesMode = (numItems == UInt32(-1));
- if (allFilesMode)
- numItems = _items.Size();
- if(numItems == 0)
- return S_OK;
- UInt32 i;
- for(i = 0; i < numItems; i++)
- {
- const CItemEx &item = _items[allFilesMode ? i : indices[i]];
- totalUnPacked += item.Size;
- totalPacked += item.PackSize;
- }
- extractCallback->SetTotal(totalUnPacked);
-
- UInt64 currentTotalUnPacked = 0, currentTotalPacked = 0;
- UInt64 currentItemUnPacked, currentItemPacked;
-
- NCompress::NLzh::NDecoder::CCoder *lzhDecoderSpec = 0;
- CMyComPtr<ICompressCoder> lzhDecoder;
- CMyComPtr<ICompressCoder> lzh1Decoder;
- CMyComPtr<ICompressCoder> arj2Decoder;
-
- NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
- CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(extractCallback, false);
-
- CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
- CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_stream);
-
- for(i = 0; i < numItems; i++, currentTotalUnPacked += currentItemUnPacked,
- currentTotalPacked += currentItemPacked)
- {
- currentItemUnPacked = 0;
- currentItemPacked = 0;
-
- lps->InSize = currentTotalPacked;
- lps->OutSize = currentTotalUnPacked;
- RINOK(lps->SetCur());
-
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode;
- askMode = testMode ? NExtract::NAskMode::kTest :
- NExtract::NAskMode::kExtract;
- Int32 index = allFilesMode ? i : indices[i];
- const CItemEx &item = _items[index];
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
-
- if (item.IsDir())
- {
- // if (!testMode)
- {
- RINOK(extractCallback->PrepareOperation(askMode));
- RINOK(extractCallback->SetOperationResult(NExtract::NOperationResult::kOK));
- }
- continue;
- }
-
- if (!testMode && (!realOutStream))
- continue;
-
- RINOK(extractCallback->PrepareOperation(askMode));
- currentItemUnPacked = item.Size;
- currentItemPacked = item.PackSize;
-
- {
- COutStreamWithCRC *outStreamSpec = new COutStreamWithCRC;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
- outStreamSpec->Init(realOutStream);
- realOutStream.Release();
-
- UInt64 pos;
- _stream->Seek(item.DataPosition, STREAM_SEEK_SET, &pos);
-
- streamSpec->Init(item.PackSize);
-
- HRESULT result = S_OK;
- Int32 opRes = NExtract::NOperationResult::kOK;
-
- if (item.IsCopyMethod())
- {
- result = copyCoder->Code(inStream, outStream, NULL, NULL, progress);
- if (result == S_OK && copyCoderSpec->TotalSize != item.PackSize)
- result = S_FALSE;
- }
- else if (item.IsLh4GroupMethod())
- {
- if (!lzhDecoder)
- {
- lzhDecoderSpec = new NCompress::NLzh::NDecoder::CCoder;
- lzhDecoder = lzhDecoderSpec;
- }
- lzhDecoderSpec->SetDictionary(item.GetNumDictBits());
- result = lzhDecoder->Code(inStream, outStream, NULL, &currentItemUnPacked, progress);
- }
- /*
- else if (item.IsLh1GroupMethod())
- {
- if (!lzh1Decoder)
- {
- lzh1DecoderSpec = new NCompress::NLzh1::NDecoder::CCoder;
- lzh1Decoder = lzh1DecoderSpec;
- }
- lzh1DecoderSpec->SetDictionary(item.GetNumDictBits());
- result = lzh1Decoder->Code(inStream, outStream, NULL, &currentItemUnPacked, progress);
- }
- */
- else
- opRes = NExtract::NOperationResult::kUnSupportedMethod;
-
- if (opRes == NExtract::NOperationResult::kOK)
- {
- if (result == S_FALSE)
- opRes = NExtract::NOperationResult::kDataError;
- else
- {
- RINOK(result);
- if (outStreamSpec->GetCRC() != item.CRC)
- opRes = NExtract::NOperationResult::kCRCError;
- }
- }
- outStream.Release();
- RINOK(extractCallback->SetOperationResult(opRes));
- }
- }
- return S_OK;
- COM_TRY_END
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzh/LzhHandler.h b/CPP/7zip/Archive/Lzh/LzhHandler.h
deleted file mode 100755
index ed504dd2..00000000
--- a/CPP/7zip/Archive/Lzh/LzhHandler.h
+++ /dev/null
@@ -1,30 +0,0 @@
-// LzhHandler.h
-
-#ifndef __LZH_HANDLER_H
-#define __LZH_HANDLER_H
-
-#include "Common/MyCom.h"
-#include "../IArchive.h"
-#include "LzhIn.h"
-
-namespace NArchive {
-namespace NLzh {
-
-class CHandler:
- public IInArchive,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP1(IInArchive)
-
- INTERFACE_IInArchive(;)
-
- CHandler();
-private:
- CObjectVector<CItemEx> _items;
- CMyComPtr<IInStream> _stream;
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhHeader.h b/CPP/7zip/Archive/Lzh/LzhHeader.h
deleted file mode 100755
index 845b9a21..00000000
--- a/CPP/7zip/Archive/Lzh/LzhHeader.h
+++ /dev/null
@@ -1,19 +0,0 @@
-// Archive/Lzh/Header.h
-
-#ifndef __ARCHIVE_LZH_HEADER_H
-#define __ARCHIVE_LZH_HEADER_H
-
-#include "Common/Types.h"
-
-namespace NArchive {
-namespace NLzh {
-
-const int kMethodIdSize = 5;
-
-const Byte kExtIdFileName = 0x01;
-const Byte kExtIdDirName = 0x02;
-const Byte kExtIdUnixTime = 0x54;
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhIn.cpp b/CPP/7zip/Archive/Lzh/LzhIn.cpp
deleted file mode 100755
index 6783654c..00000000
--- a/CPP/7zip/Archive/Lzh/LzhIn.cpp
+++ /dev/null
@@ -1,172 +0,0 @@
-// Archive/LzhIn.cpp
-
-#include "StdAfx.h"
-
-#include "Common/StringConvert.h"
-#include "Common/Buffer.h"
-
-#include "../../Common/StreamUtils.h"
-
-#include "LzhIn.h"
-
-namespace NArchive {
-namespace NLzh {
-
-HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 &processedSize)
-{
- size_t realProcessedSize = size;
- RINOK(ReadStream(m_Stream, data, &realProcessedSize));
- processedSize = (UInt32)realProcessedSize;
- m_Position += processedSize;
- return S_OK;
-}
-
-HRESULT CInArchive::CheckReadBytes(void *data, UInt32 size)
-{
- UInt32 processedSize;
- RINOK(ReadBytes(data, size, processedSize));
- return (processedSize == size) ? S_OK: S_FALSE;
-}
-
-HRESULT CInArchive::Open(IInStream *inStream)
-{
- RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Position));
- m_Stream = inStream;
- return S_OK;
-}
-
-static const Byte *ReadUInt32(const Byte *p, UInt32 &v)
-{
- v = 0;
- for (int i = 0; i < 4; i++)
- v |= ((UInt32)(*p++) << (i * 8));
- return p;
-}
-
-static const Byte *ReadUInt16(const Byte *p, UInt16 &v)
-{
- v = 0;
- for (int i = 0; i < 2; i++)
- v |= ((UInt16)(*p++) << (i * 8));
- return p;
-}
-
-static const Byte *ReadString(const Byte *p, size_t size, AString &s)
-{
- s.Empty();
- for (size_t i = 0; i < size; i++)
- {
- char c = p[i];
- if (c == 0)
- break;
- s += c;
- }
- return p + size;
-}
-
-static Byte CalcSum(const Byte *data, size_t size)
-{
- Byte sum = 0;
- for (size_t i = 0; i < size; i++)
- sum = (Byte)(sum + data[i]);
- return sum;
-}
-
-HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
-{
- filled = false;
-
- UInt32 processedSize;
- Byte startHeader[2];
- RINOK(ReadBytes(startHeader, 2, processedSize))
- if (processedSize == 0)
- return S_OK;
- if (processedSize == 1)
- return (startHeader[0] == 0) ? S_OK: S_FALSE;
- if (startHeader[0] == 0 && startHeader[1] == 0)
- return S_OK;
-
- Byte header[256];
- const UInt32 kBasicPartSize = 22;
- RINOK(ReadBytes(header, kBasicPartSize, processedSize));
- if (processedSize != kBasicPartSize)
- return (startHeader[0] == 0) ? S_OK: S_FALSE;
-
- const Byte *p = header;
- memmove(item.Method, p, kMethodIdSize);
- if (!item.IsValidMethod())
- return S_OK;
- p += kMethodIdSize;
- p = ReadUInt32(p, item.PackSize);
- p = ReadUInt32(p, item.Size);
- p = ReadUInt32(p, item.ModifiedTime);
- item.Attributes = *p++;
- item.Level = *p++;
- if (item.Level > 2)
- return S_FALSE;
- UInt32 headerSize;
- if (item.Level < 2)
- {
- headerSize = startHeader[0];
- if (headerSize < kBasicPartSize)
- return S_FALSE;
- UInt32 remain = headerSize - kBasicPartSize;
- RINOK(CheckReadBytes(header + kBasicPartSize, remain));
- if (startHeader[1] != CalcSum(header, headerSize))
- return S_FALSE;
- size_t nameLength = *p++;
- if ((p - header) + nameLength + 2 > headerSize)
- return S_FALSE;
- p = ReadString(p, nameLength, item.Name);
- }
- else
- headerSize = startHeader[0] | ((UInt32)startHeader[1] << 8);
- p = ReadUInt16(p, item.CRC);
- if (item.Level != 0)
- {
- if (item.Level == 2)
- {
- RINOK(CheckReadBytes(header + kBasicPartSize, 2));
- }
- if ((size_t)(p - header) + 3 > headerSize)
- return S_FALSE;
- item.OsId = *p++;
- UInt16 nextSize;
- p = ReadUInt16(p, nextSize);
- while (nextSize != 0)
- {
- if (nextSize < 3)
- return S_FALSE;
- if (item.Level == 1)
- {
- if (item.PackSize < nextSize)
- return S_FALSE;
- item.PackSize -= nextSize;
- }
- CExtension ext;
- RINOK(CheckReadBytes(&ext.Type, 1))
- nextSize -= 3;
- ext.Data.SetCapacity(nextSize);
- RINOK(CheckReadBytes((Byte *)ext.Data, nextSize))
- item.Extensions.Add(ext);
- Byte hdr2[2];
- RINOK(CheckReadBytes(hdr2, 2));
- ReadUInt16(hdr2, nextSize);
- }
- }
- item.DataPosition = m_Position;
- filled = true;
- return S_OK;
-}
-
-HRESULT CInArchive::Skeep(UInt64 numBytes)
-{
- UInt64 newPostion;
- RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));
- m_Position += numBytes;
- if (m_Position != newPostion)
- return E_FAIL;
- return S_OK;
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzh/LzhIn.h b/CPP/7zip/Archive/Lzh/LzhIn.h
deleted file mode 100755
index 344a133f..00000000
--- a/CPP/7zip/Archive/Lzh/LzhIn.h
+++ /dev/null
@@ -1,29 +0,0 @@
-// Archive/LzhIn.h
-
-#ifndef __ARCHIVE_LZHIN_H
-#define __ARCHIVE_LZHIN_H
-
-#include "Common/MyCom.h"
-#include "../../IStream.h"
-
-#include "LzhItem.h"
-
-namespace NArchive {
-namespace NLzh {
-
-class CInArchive
-{
- CMyComPtr<IInStream> m_Stream;
- UInt64 m_Position;
-
- HRESULT ReadBytes(void *data, UInt32 size, UInt32 &processedSize);
- HRESULT CheckReadBytes(void *data, UInt32 size);
-public:
- HRESULT Open(IInStream *inStream);
- HRESULT GetNextItem(bool &filled, CItemEx &itemInfo);
- HRESULT Skeep(UInt64 numBytes);
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhItem.h b/CPP/7zip/Archive/Lzh/LzhItem.h
deleted file mode 100755
index 494a65bf..00000000
--- a/CPP/7zip/Archive/Lzh/LzhItem.h
+++ /dev/null
@@ -1,172 +0,0 @@
-// Archive/LzhItem.h
-
-#ifndef __ARCHIVE_LZH_ITEM_H
-#define __ARCHIVE_LZH_ITEM_H
-
-#include "Common/Types.h"
-#include "Common/MyString.h"
-#include "Common/Buffer.h"
-#include "LzhHeader.h"
-
-namespace NArchive {
-namespace NLzh {
-
-struct CExtension
-{
- Byte Type;
- CByteBuffer Data;
- AString GetString() const
- {
- AString s;
- for (size_t i = 0; i < Data.GetCapacity(); i++)
- {
- char c = (char)Data[i];
- if (c == 0)
- break;
- s += c;
- }
- return s;
- }
-};
-
-struct CItem
-{
-public:
- AString Name;
- Byte Method[kMethodIdSize];
- UInt32 PackSize;
- UInt32 Size;
- UInt32 ModifiedTime;
- Byte Attributes;
- Byte Level;
- UInt16 CRC;
- Byte OsId;
- CObjectVector<CExtension> Extensions;
-
- bool IsValidMethod() const { return (Method[0] == '-' && Method[1] == 'l' && Method[4] == '-'); }
- bool IsLhMethod() const {return (IsValidMethod() && Method[2] == 'h'); }
- bool IsDir() const {return (IsLhMethod() && Method[3] == 'd'); }
-
- bool IsCopyMethod() const
- {
- return (IsLhMethod() && Method[3] == '0') ||
- (IsValidMethod() && Method[2] == 'z' && Method[3] == '4');
- }
-
- bool IsLh1GroupMethod() const
- {
- if (!IsLhMethod())
- return false;
- switch(Method[3])
- {
- case '1':
- return true;
- }
- return false;
- }
-
- bool IsLh4GroupMethod() const
- {
- if (!IsLhMethod())
- return false;
- switch(Method[3])
- {
- case '4':
- case '5':
- case '6':
- case '7':
- return true;
- }
- return false;
- }
-
- int GetNumDictBits() const
- {
- if (!IsLhMethod())
- return 0;
- switch(Method[3])
- {
- case '1':
- return 12;
- case '2':
- return 13;
- case '3':
- return 13;
- case '4':
- return 12;
- case '5':
- return 13;
- case '6':
- return 15;
- case '7':
- return 16;
- }
- return 0;
- }
-
- int FindExt(Byte type) const
- {
- for (int i = 0; i < Extensions.Size(); i++)
- if (Extensions[i].Type == type)
- return i;
- return -1;
- }
- bool GetUnixTime(UInt32 &value) const
- {
- int index = FindExt(kExtIdUnixTime);
- if (index < 0)
- {
- if (Level == 2)
- {
- value = ModifiedTime;
- return true;
- }
- return false;
- }
- const Byte *data = (const Byte *)(Extensions[index].Data);
- value = data[0] |
- ((UInt32)data[1] << 8) |
- ((UInt32)data[2] << 16) |
- ((UInt32)data[3] << 24);
- return true;
- }
-
- AString GetDirName() const
- {
- int index = FindExt(kExtIdDirName);
- if (index < 0)
- return AString();
- return Extensions[index].GetString();
- }
-
- AString GetFileName() const
- {
- int index = FindExt(kExtIdFileName);
- if (index < 0)
- return Name;
- return Extensions[index].GetString();
- }
-
- AString GetName() const
- {
- AString dirName = GetDirName();
- dirName.Replace((char)(unsigned char)0xFF, '\\');
- if (!dirName.IsEmpty())
- {
- char c = dirName[dirName.Length() - 1];
- if (c != '\\')
- dirName += '\\';
- }
- return dirName + GetFileName();
- }
-};
-
-class CItemEx: public CItem
-{
-public:
- UInt64 DataPosition;
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.cpp b/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.cpp
deleted file mode 100755
index 2281a884..00000000
--- a/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.cpp
+++ /dev/null
@@ -1,27 +0,0 @@
-// LzhOutStreamWithCRC.cpp
-
-#include "StdAfx.h"
-
-#include "LzhOutStreamWithCRC.h"
-
-namespace NArchive {
-namespace NLzh {
-
-STDMETHODIMP COutStreamWithCRC::Write(const void *data, UInt32 size, UInt32 *processedSize)
-{
- UInt32 realProcessedSize;
- HRESULT result;
- if(!_stream)
- {
- realProcessedSize = size;
- result = S_OK;
- }
- else
- result = _stream->Write(data, size, &realProcessedSize);
- _crc.Update(data, realProcessedSize);
- if(processedSize != NULL)
- *processedSize = realProcessedSize;
- return result;
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.h b/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.h
deleted file mode 100755
index fd73f4ae..00000000
--- a/CPP/7zip/Archive/Lzh/LzhOutStreamWithCRC.h
+++ /dev/null
@@ -1,38 +0,0 @@
-// LzhOutStreamWithCRC.h
-
-#ifndef __LZHOUTSTREAMWITHCRC_H
-#define __LZHOUTSTREAMWITHCRC_H
-
-#include "LzhCRC.h"
-#include "../../../Common/MyCom.h"
-#include "../../IStream.h"
-
-namespace NArchive {
-namespace NLzh {
-
-class COutStreamWithCRC:
- public ISequentialOutStream,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP
-
- STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
-private:
- CCRC _crc;
- CMyComPtr<ISequentialOutStream> _stream;
-public:
- void Init(ISequentialOutStream *stream)
- {
- _stream = stream;
- _crc.Init();
- }
- void ReleaseStream() { _stream.Release(); }
- UInt32 GetCRC() const { return _crc.GetDigest(); }
- void InitCRC() { _crc.Init(); }
-
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzh/LzhRegister.cpp b/CPP/7zip/Archive/Lzh/LzhRegister.cpp
deleted file mode 100755
index b9b1d473..00000000
--- a/CPP/7zip/Archive/Lzh/LzhRegister.cpp
+++ /dev/null
@@ -1,13 +0,0 @@
-// LzhRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "LzhHandler.h"
-static IInArchive *CreateArc() { return new NArchive::NLzh::CHandler; }
-
-static CArcInfo g_ArcInfo =
- { L"Lzh", L"lzh lha", 0, 6, { '-', 'l' }, 2, false, CreateArc, 0 };
-
-REGISTER_ARC(Lzh)
diff --git a/CPP/7zip/Archive/Lzh/StdAfx.h b/CPP/7zip/Archive/Lzh/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/Lzh/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/LzhHandler.cpp b/CPP/7zip/Archive/LzhHandler.cpp
new file mode 100755
index 00000000..19a9516a
--- /dev/null
+++ b/CPP/7zip/Archive/LzhHandler.cpp
@@ -0,0 +1,783 @@
+// LzhHandler.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/Buffer.h"
+#include "Common/ComTry.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/PropVariant.h"
+#include "Windows/Time.h"
+
+#include "../ICoder.h"
+
+#include "../Common/LimitedStreams.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+#include "../Compress/LzhDecoder.h"
+
+#include "IArchive.h"
+
+#include "Common/ItemNameUtils.h"
+
+using namespace NWindows;
+using namespace NTime;
+
+#define Get16(p) GetUi16(p)
+#define Get32(p) GetUi32(p)
+
+namespace NArchive {
+namespace NLzh{
+
+const int kMethodIdSize = 5;
+
+const Byte kExtIdFileName = 0x01;
+const Byte kExtIdDirName = 0x02;
+const Byte kExtIdUnixTime = 0x54;
+
+struct CExtension
+{
+ Byte Type;
+ CByteBuffer Data;
+ AString GetString() const
+ {
+ AString s;
+ for (size_t i = 0; i < Data.GetCapacity(); i++)
+ {
+ char c = (char)Data[i];
+ if (c == 0)
+ break;
+ s += c;
+ }
+ return s;
+ }
+};
+
+struct CItem
+{
+ AString Name;
+ Byte Method[kMethodIdSize];
+ Byte Attributes;
+ Byte Level;
+ Byte OsId;
+ UInt32 PackSize;
+ UInt32 Size;
+ UInt32 ModifiedTime;
+ UInt16 CRC;
+ CObjectVector<CExtension> Extensions;
+
+ bool IsValidMethod() const { return (Method[0] == '-' && Method[1] == 'l' && Method[4] == '-'); }
+ bool IsLhMethod() const {return (IsValidMethod() && Method[2] == 'h'); }
+ bool IsDir() const {return (IsLhMethod() && Method[3] == 'd'); }
+
+ bool IsCopyMethod() const
+ {
+ return (IsLhMethod() && Method[3] == '0') ||
+ (IsValidMethod() && Method[2] == 'z' && Method[3] == '4');
+ }
+
+ bool IsLh1GroupMethod() const
+ {
+ if (!IsLhMethod())
+ return false;
+ switch(Method[3])
+ {
+ case '1':
+ return true;
+ }
+ return false;
+ }
+
+ bool IsLh4GroupMethod() const
+ {
+ if (!IsLhMethod())
+ return false;
+ switch(Method[3])
+ {
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ return true;
+ }
+ return false;
+ }
+
+ int GetNumDictBits() const
+ {
+ if (!IsLhMethod())
+ return 0;
+ switch(Method[3])
+ {
+ case '1': return 12;
+ case '2': return 13;
+ case '3': return 13;
+ case '4': return 12;
+ case '5': return 13;
+ case '6': return 15;
+ case '7': return 16;
+ }
+ return 0;
+ }
+
+ int FindExt(Byte type) const
+ {
+ for (int i = 0; i < Extensions.Size(); i++)
+ if (Extensions[i].Type == type)
+ return i;
+ return -1;
+ }
+ bool GetUnixTime(UInt32 &value) const
+ {
+ int index = FindExt(kExtIdUnixTime);
+ if (index < 0)
+ {
+ if (Level == 2)
+ {
+ value = ModifiedTime;
+ return true;
+ }
+ return false;
+ }
+ const Byte *data = (const Byte *)(Extensions[index].Data);
+ value = GetUi32(data);
+ return true;
+ }
+
+ AString GetDirName() const
+ {
+ int index = FindExt(kExtIdDirName);
+ if (index < 0)
+ return AString();
+ return Extensions[index].GetString();
+ }
+
+ AString GetFileName() const
+ {
+ int index = FindExt(kExtIdFileName);
+ if (index < 0)
+ return Name;
+ return Extensions[index].GetString();
+ }
+
+ AString GetName() const
+ {
+ AString dirName = GetDirName();
+ dirName.Replace((char)(unsigned char)0xFF, '\\');
+ if (!dirName.IsEmpty())
+ {
+ char c = dirName[dirName.Length() - 1];
+ if (c != '\\')
+ dirName += '\\';
+ }
+ return dirName + GetFileName();
+ }
+};
+
+struct CItemEx: public CItem
+{
+ UInt64 DataPosition;
+};
+
+class CInArchive
+{
+ CMyComPtr<IInStream> m_Stream;
+ UInt64 m_Position;
+
+ HRESULT ReadBytes(void *data, UInt32 size, UInt32 &processedSize);
+ HRESULT CheckReadBytes(void *data, UInt32 size);
+public:
+ HRESULT Open(IInStream *inStream);
+ HRESULT GetNextItem(bool &filled, CItemEx &itemInfo);
+ HRESULT Skip(UInt64 numBytes);
+};
+
+HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 &processedSize)
+{
+ size_t realProcessedSize = size;
+ RINOK(ReadStream(m_Stream, data, &realProcessedSize));
+ processedSize = (UInt32)realProcessedSize;
+ m_Position += processedSize;
+ return S_OK;
+}
+
+HRESULT CInArchive::CheckReadBytes(void *data, UInt32 size)
+{
+ UInt32 processedSize;
+ RINOK(ReadBytes(data, size, processedSize));
+ return (processedSize == size) ? S_OK: S_FALSE;
+}
+
+HRESULT CInArchive::Open(IInStream *inStream)
+{
+ RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Position));
+ m_Stream = inStream;
+ return S_OK;
+}
+
+static const Byte *ReadUInt16(const Byte *p, UInt16 &v)
+{
+ v = Get16(p);
+ return p + 2;
+}
+
+static const Byte *ReadString(const Byte *p, size_t size, AString &s)
+{
+ s.Empty();
+ for (size_t i = 0; i < size; i++)
+ {
+ char c = p[i];
+ if (c == 0)
+ break;
+ s += c;
+ }
+ return p + size;
+}
+
+static Byte CalcSum(const Byte *data, size_t size)
+{
+ Byte sum = 0;
+ for (size_t i = 0; i < size; i++)
+ sum = (Byte)(sum + data[i]);
+ return sum;
+}
+
+HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item)
+{
+ filled = false;
+
+ UInt32 processedSize;
+ Byte startHeader[2];
+ RINOK(ReadBytes(startHeader, 2, processedSize))
+ if (processedSize == 0)
+ return S_OK;
+ if (processedSize == 1)
+ return (startHeader[0] == 0) ? S_OK: S_FALSE;
+ if (startHeader[0] == 0 && startHeader[1] == 0)
+ return S_OK;
+
+ Byte header[256];
+ const UInt32 kBasicPartSize = 22;
+ RINOK(ReadBytes(header, kBasicPartSize, processedSize));
+ if (processedSize != kBasicPartSize)
+ return (startHeader[0] == 0) ? S_OK: S_FALSE;
+
+ const Byte *p = header;
+ memmove(item.Method, p, kMethodIdSize);
+ if (!item.IsValidMethod())
+ return S_OK;
+ p += kMethodIdSize;
+ item.PackSize = Get32(p);
+ item.Size = Get32(p + 4);
+ item.ModifiedTime = Get32(p + 8);
+ item.Attributes = p[12];
+ item.Level = p[13];
+ p += 14;
+ if (item.Level > 2)
+ return S_FALSE;
+ UInt32 headerSize;
+ if (item.Level < 2)
+ {
+ headerSize = startHeader[0];
+ if (headerSize < kBasicPartSize)
+ return S_FALSE;
+ UInt32 remain = headerSize - kBasicPartSize;
+ RINOK(CheckReadBytes(header + kBasicPartSize, remain));
+ if (startHeader[1] != CalcSum(header, headerSize))
+ return S_FALSE;
+ size_t nameLength = *p++;
+ if ((p - header) + nameLength + 2 > headerSize)
+ return S_FALSE;
+ p = ReadString(p, nameLength, item.Name);
+ }
+ else
+ headerSize = startHeader[0] | ((UInt32)startHeader[1] << 8);
+ p = ReadUInt16(p, item.CRC);
+ if (item.Level != 0)
+ {
+ if (item.Level == 2)
+ {
+ RINOK(CheckReadBytes(header + kBasicPartSize, 2));
+ }
+ if ((size_t)(p - header) + 3 > headerSize)
+ return S_FALSE;
+ item.OsId = *p++;
+ UInt16 nextSize;
+ p = ReadUInt16(p, nextSize);
+ while (nextSize != 0)
+ {
+ if (nextSize < 3)
+ return S_FALSE;
+ if (item.Level == 1)
+ {
+ if (item.PackSize < nextSize)
+ return S_FALSE;
+ item.PackSize -= nextSize;
+ }
+ CExtension ext;
+ RINOK(CheckReadBytes(&ext.Type, 1))
+ nextSize -= 3;
+ ext.Data.SetCapacity(nextSize);
+ RINOK(CheckReadBytes((Byte *)ext.Data, nextSize))
+ item.Extensions.Add(ext);
+ Byte hdr2[2];
+ RINOK(CheckReadBytes(hdr2, 2));
+ ReadUInt16(hdr2, nextSize);
+ }
+ }
+ item.DataPosition = m_Position;
+ filled = true;
+ return S_OK;
+}
+
+HRESULT CInArchive::Skip(UInt64 numBytes)
+{
+ UInt64 newPostion;
+ RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));
+ m_Position += numBytes;
+ if (m_Position != newPostion)
+ return E_FAIL;
+ return S_OK;
+}
+
+struct COsPair
+{
+ Byte Id;
+ const char *Name;
+};
+
+static COsPair g_OsPairs[] =
+{
+ { 0, "MS-DOS" },
+ { 'M', "MS-DOS" },
+ { '2', "OS/2" },
+ { '9', "OS9" },
+ { 'K', "OS/68K" },
+ { '3', "OS/386" },
+ { 'H', "HUMAN" },
+ { 'U', "UNIX" },
+ { 'C', "CP/M" },
+ { 'F', "FLEX" },
+ { 'm', "Mac" },
+ { 'R', "Runser" },
+ { 'T', "TownsOS" },
+ { 'X', "XOSK" },
+ { 'w', "Windows 95" },
+ { 'W', "Windows NT" },
+ { 'J', "Java VM" }
+};
+
+static const char *kUnknownOS = "Unknown";
+
+static const char *GetOS(Byte osId)
+{
+ for (int i = 0; i < sizeof(g_OsPairs) / sizeof(g_OsPairs[0]); i++)
+ if (g_OsPairs[i].Id == osId)
+ return g_OsPairs[i].Name;
+ return kUnknownOS;
+};
+
+static STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidIsDir, VT_BOOL},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ // { NULL, kpidAttrib, VT_UI4},
+ { NULL, kpidCRC, VT_UI4},
+ { NULL, kpidMethod, VT_BSTR},
+ { NULL, kpidHostOS, VT_BSTR}
+};
+
+class CCRC
+{
+ UInt16 _value;
+public:
+ static UInt16 Table[256];
+ static void InitTable();
+
+ CCRC(): _value(0){};
+ void Init() { _value = 0; }
+ void Update(const void *data, size_t size);
+ UInt16 GetDigest() const { return _value; }
+};
+
+static const UInt16 kCRCPoly = 0xA001;
+
+UInt16 CCRC::Table[256];
+
+void CCRC::InitTable()
+{
+ for (UInt32 i = 0; i < 256; i++)
+ {
+ UInt32 r = i;
+ for (int j = 0; j < 8; j++)
+ if (r & 1)
+ r = (r >> 1) ^ kCRCPoly;
+ else
+ r >>= 1;
+ CCRC::Table[i] = (UInt16)r;
+ }
+}
+
+class CCRCTableInit
+{
+public:
+ CCRCTableInit() { CCRC::InitTable(); }
+} g_CRCTableInit;
+
+void CCRC::Update(const void *data, size_t size)
+{
+ UInt16 v = _value;
+ const Byte *p = (const Byte *)data;
+ for (; size > 0; size--, p++)
+ v = (UInt16)(Table[((Byte)(v)) ^ *p] ^ (v >> 8));
+ _value = v;
+}
+
+
+class COutStreamWithCRC:
+ public ISequentialOutStream,
+ public CMyUnknownImp
+{
+public:
+ MY_UNKNOWN_IMP
+
+ STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
+private:
+ CCRC _crc;
+ CMyComPtr<ISequentialOutStream> _stream;
+public:
+ void Init(ISequentialOutStream *stream)
+ {
+ _stream = stream;
+ _crc.Init();
+ }
+ void ReleaseStream() { _stream.Release(); }
+ UInt32 GetCRC() const { return _crc.GetDigest(); }
+ void InitCRC() { _crc.Init(); }
+
+};
+
+STDMETHODIMP COutStreamWithCRC::Write(const void *data, UInt32 size, UInt32 *processedSize)
+{
+ UInt32 realProcessedSize;
+ HRESULT result;
+ if(!_stream)
+ {
+ realProcessedSize = size;
+ result = S_OK;
+ }
+ else
+ result = _stream->Write(data, size, &realProcessedSize);
+ _crc.Update(data, realProcessedSize);
+ if(processedSize != NULL)
+ *processedSize = realProcessedSize;
+ return result;
+}
+
+class CHandler:
+ public IInArchive,
+ public CMyUnknownImp
+{
+ CObjectVector<CItemEx> _items;
+ CMyComPtr<IInStream> _stream;
+public:
+ MY_UNKNOWN_IMP1(IInArchive)
+ INTERFACE_IInArchive(;)
+ CHandler();
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_NO
+
+CHandler::CHandler() {}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = _items.Size();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ const CItemEx &item = _items[index];
+ switch(propID)
+ {
+ case kpidPath:
+ {
+ UString s = NItemName::WinNameToOSName(MultiByteToUnicodeString(item.GetName(), CP_OEMCP));
+ if (!s.IsEmpty())
+ {
+ if (s[s.Length() - 1] == WCHAR_PATH_SEPARATOR)
+ s.Delete(s.Length() - 1);
+ prop = s;
+ }
+ break;
+ }
+ case kpidIsDir: prop = item.IsDir(); break;
+ case kpidSize: prop = item.Size; break;
+ case kpidPackSize: prop = item.PackSize; break;
+ case kpidCRC: prop = (UInt32)item.CRC; break;
+ case kpidHostOS: prop = GetOS(item.OsId); break;
+ case kpidMTime:
+ {
+ FILETIME utc;
+ UInt32 unixTime;
+ if (item.GetUnixTime(unixTime))
+ NTime::UnixTimeToFileTime(unixTime, utc);
+ else
+ {
+ FILETIME localFileTime;
+ if (DosTimeToFileTime(item.ModifiedTime, localFileTime))
+ {
+ if (!LocalFileTimeToFileTime(&localFileTime, &utc))
+ utc.dwHighDateTime = utc.dwLowDateTime = 0;
+ }
+ else
+ utc.dwHighDateTime = utc.dwLowDateTime = 0;
+ }
+ prop = utc;
+ break;
+ }
+ // case kpidAttrib: prop = (UInt32)item.Attributes; break;
+ case kpidMethod:
+ {
+ char method2[kMethodIdSize + 1];
+ method2[kMethodIdSize] = 0;
+ memcpy(method2, item.Method, kMethodIdSize);
+ prop = method2;
+ break;
+ }
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream,
+ const UInt64 * /* maxCheckStartPosition */, IArchiveOpenCallback *callback)
+{
+ COM_TRY_BEGIN
+ try
+ {
+ _items.Clear();
+ CInArchive archive;
+
+ UInt64 endPos = 0;
+ bool needSetTotal = true;
+
+ if (callback != NULL)
+ {
+ RINOK(stream->Seek(0, STREAM_SEEK_END, &endPos));
+ RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
+ }
+
+ RINOK(archive.Open(stream));
+ for (;;)
+ {
+ CItemEx item;
+ bool filled;
+ HRESULT result = archive.GetNextItem(filled, item);
+ if (result == S_FALSE)
+ return S_FALSE;
+ if (result != S_OK)
+ return S_FALSE;
+ if (!filled)
+ break;
+ _items.Add(item);
+ archive.Skip(item.PackSize);
+ if (callback != NULL)
+ {
+ if (needSetTotal)
+ {
+ RINOK(callback->SetTotal(NULL, &endPos));
+ needSetTotal = false;
+ }
+ if (_items.Size() % 100 == 0)
+ {
+ UInt64 numFiles = _items.Size();
+ UInt64 numBytes = item.DataPosition;
+ RINOK(callback->SetCompleted(&numFiles, &numBytes));
+ }
+ }
+ }
+ if (_items.IsEmpty())
+ return S_FALSE;
+
+ _stream = stream;
+ }
+ catch(...)
+ {
+ return S_FALSE;
+ }
+ COM_TRY_END
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _items.Clear();
+ _stream.Release();
+ return S_OK;
+}
+
+
+
+//////////////////////////////////////
+// CHandler::DecompressItems
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 testModeSpec, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool testMode = (testModeSpec != 0);
+ UInt64 totalUnPacked = 0, totalPacked = 0;
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (allFilesMode)
+ numItems = _items.Size();
+ if(numItems == 0)
+ return S_OK;
+ UInt32 i;
+ for(i = 0; i < numItems; i++)
+ {
+ const CItemEx &item = _items[allFilesMode ? i : indices[i]];
+ totalUnPacked += item.Size;
+ totalPacked += item.PackSize;
+ }
+ extractCallback->SetTotal(totalUnPacked);
+
+ UInt64 currentTotalUnPacked = 0, currentTotalPacked = 0;
+ UInt64 currentItemUnPacked, currentItemPacked;
+
+ NCompress::NLzh::NDecoder::CCoder *lzhDecoderSpec = 0;
+ CMyComPtr<ICompressCoder> lzhDecoder;
+ CMyComPtr<ICompressCoder> lzh1Decoder;
+ CMyComPtr<ICompressCoder> arj2Decoder;
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
+ CMyComPtr<ISequentialInStream> inStream(streamSpec);
+ streamSpec->SetStream(_stream);
+
+ for(i = 0; i < numItems; i++, currentTotalUnPacked += currentItemUnPacked,
+ currentTotalPacked += currentItemPacked)
+ {
+ currentItemUnPacked = 0;
+ currentItemPacked = 0;
+
+ lps->InSize = currentTotalPacked;
+ lps->OutSize = currentTotalUnPacked;
+ RINOK(lps->SetCur());
+
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode;
+ askMode = testMode ? NExtract::NAskMode::kTest :
+ NExtract::NAskMode::kExtract;
+ Int32 index = allFilesMode ? i : indices[i];
+ const CItemEx &item = _items[index];
+ RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
+
+ if (item.IsDir())
+ {
+ // if (!testMode)
+ {
+ RINOK(extractCallback->PrepareOperation(askMode));
+ RINOK(extractCallback->SetOperationResult(NExtract::NOperationResult::kOK));
+ }
+ continue;
+ }
+
+ if (!testMode && (!realOutStream))
+ continue;
+
+ RINOK(extractCallback->PrepareOperation(askMode));
+ currentItemUnPacked = item.Size;
+ currentItemPacked = item.PackSize;
+
+ {
+ COutStreamWithCRC *outStreamSpec = new COutStreamWithCRC;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+ outStreamSpec->Init(realOutStream);
+ realOutStream.Release();
+
+ UInt64 pos;
+ _stream->Seek(item.DataPosition, STREAM_SEEK_SET, &pos);
+
+ streamSpec->Init(item.PackSize);
+
+ HRESULT result = S_OK;
+ Int32 opRes = NExtract::NOperationResult::kOK;
+
+ if (item.IsCopyMethod())
+ {
+ result = copyCoder->Code(inStream, outStream, NULL, NULL, progress);
+ if (result == S_OK && copyCoderSpec->TotalSize != item.PackSize)
+ result = S_FALSE;
+ }
+ else if (item.IsLh4GroupMethod())
+ {
+ if (!lzhDecoder)
+ {
+ lzhDecoderSpec = new NCompress::NLzh::NDecoder::CCoder;
+ lzhDecoder = lzhDecoderSpec;
+ }
+ lzhDecoderSpec->SetDictionary(item.GetNumDictBits());
+ result = lzhDecoder->Code(inStream, outStream, NULL, &currentItemUnPacked, progress);
+ }
+ /*
+ else if (item.IsLh1GroupMethod())
+ {
+ if (!lzh1Decoder)
+ {
+ lzh1DecoderSpec = new NCompress::NLzh1::NDecoder::CCoder;
+ lzh1Decoder = lzh1DecoderSpec;
+ }
+ lzh1DecoderSpec->SetDictionary(item.GetNumDictBits());
+ result = lzh1Decoder->Code(inStream, outStream, NULL, &currentItemUnPacked, progress);
+ }
+ */
+ else
+ opRes = NExtract::NOperationResult::kUnSupportedMethod;
+
+ if (opRes == NExtract::NOperationResult::kOK)
+ {
+ if (result == S_FALSE)
+ opRes = NExtract::NOperationResult::kDataError;
+ else
+ {
+ RINOK(result);
+ if (outStreamSpec->GetCRC() != item.CRC)
+ opRes = NExtract::NOperationResult::kCRCError;
+ }
+ }
+ outStream.Release();
+ RINOK(extractCallback->SetOperationResult(opRes));
+ }
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"Lzh", L"lzh lha", 0, 6, { '-', 'l' }, 2, false, CreateArc, 0 };
+
+REGISTER_ARC(Lzh)
+
+}}
diff --git a/CPP/7zip/Archive/Lzma/LzmaArcRegister.cpp b/CPP/7zip/Archive/Lzma/LzmaArcRegister.cpp
deleted file mode 100755
index bbeb177b..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaArcRegister.cpp
+++ /dev/null
@@ -1,14 +0,0 @@
-// LzmaArcRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "LzmaHandler.h"
-
-static IInArchive *CreateArc() { return new NArchive::NLzma::CHandler; }
-
-static CArcInfo g_ArcInfo =
- { L"Lzma", L"lzma lzma86", 0, 0xA, {0 }, 0, true, CreateArc, NULL };
-
-REGISTER_ARC(Lzma)
diff --git a/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp b/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp
deleted file mode 100755
index 26c1092f..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp
+++ /dev/null
@@ -1,86 +0,0 @@
-// LzmaFiltersDecode.cpp
-
-#include "StdAfx.h"
-
-#include "LzmaFiltersDecode.h"
-
-namespace NArchive {
-namespace NLzma {
-
-static const UInt64 k_LZMA = 0x030101;
-static const UInt64 k_BCJ = 0x03030103;
-
-HRESULT CDecoder::Code(
- DECL_EXTERNAL_CODECS_LOC_VARS
- const CHeader &block,
- ISequentialInStream *inStream, ISequentialOutStream *outStream,
- UInt64 *inProcessedSize, ICompressProgressInfo *progress)
-{
- *inProcessedSize = (UInt64)(Int64)-1;
-
- if (block.FilterMethod > 1)
- return E_NOTIMPL;
-
- if (!_lzmaDecoder)
- {
- RINOK(CreateCoder(EXTERNAL_CODECS_LOC_VARS k_LZMA, _lzmaDecoder, false));
- if (_lzmaDecoder == 0)
- return E_NOTIMPL;
- }
-
- {
- CMyComPtr<ICompressSetDecoderProperties2> setDecoderProperties;
- _lzmaDecoder.QueryInterface(IID_ICompressSetDecoderProperties2, &setDecoderProperties);
- if (!setDecoderProperties)
- return E_NOTIMPL;
- RINOK(setDecoderProperties->SetDecoderProperties2(block.LzmaProps, 5));
- }
-
- bool filteredMode = (block.FilterMethod == 1);
-
- CMyComPtr<ICompressSetOutStream> setOutStream;
-
- if (filteredMode)
- {
- if (!_bcjStream)
- {
- CMyComPtr<ICompressCoder> coder;
- RINOK(CreateCoder(EXTERNAL_CODECS_LOC_VARS k_BCJ, coder, false));
- if (!coder)
- return E_NOTIMPL;
- coder.QueryInterface(IID_ISequentialOutStream, &_bcjStream);
- if (!_bcjStream)
- return E_NOTIMPL;
- }
-
- _bcjStream.QueryInterface(IID_ICompressSetOutStream, &setOutStream);
- if (!setOutStream)
- return E_NOTIMPL;
- RINOK(setOutStream->SetOutStream(outStream));
- outStream = _bcjStream;
- }
-
- const UInt64 *unpackSize = block.HasUnpackSize() ? &block.UnpackSize : NULL;
- RINOK(_lzmaDecoder->Code(inStream, outStream, NULL, unpackSize, progress));
-
- if (filteredMode)
- {
- CMyComPtr<IOutStreamFlush> flush;
- _bcjStream.QueryInterface(IID_IOutStreamFlush, &flush);
- if (flush)
- {
- RINOK(flush->Flush());
- }
- RINOK(setOutStream->ReleaseOutStream());
- }
-
- CMyComPtr<ICompressGetInStreamProcessedSize> getInStreamProcessedSize;
- _lzmaDecoder.QueryInterface(IID_ICompressGetInStreamProcessedSize, &getInStreamProcessedSize);
- if (getInStreamProcessedSize)
- {
- RINOK(getInStreamProcessedSize->GetInStreamProcessedSize(inProcessedSize));
- }
- return S_OK;
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.h b/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.h
deleted file mode 100755
index 36de4966..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.h
+++ /dev/null
@@ -1,26 +0,0 @@
-// LzmaFiltersDecode.h
-
-#ifndef __LZMA_FILTERS_DECODE_H
-#define __LZMA_FILTERS_DECODE_H
-
-#include "../../Common/CreateCoder.h"
-
-#include "LzmaItem.h"
-
-namespace NArchive {
-namespace NLzma {
-
-class CDecoder
-{
- CMyComPtr<ICompressCoder> _lzmaDecoder;
- CMyComPtr<ISequentialOutStream> _bcjStream;
-public:
- HRESULT Code(DECL_EXTERNAL_CODECS_LOC_VARS
- const CHeader &block,
- ISequentialInStream *inStream, ISequentialOutStream *outStream,
- UInt64 *inProcessedSize, ICompressProgressInfo *progress);
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzma/LzmaHandler.cpp b/CPP/7zip/Archive/Lzma/LzmaHandler.cpp
deleted file mode 100755
index c434595d..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaHandler.cpp
+++ /dev/null
@@ -1,243 +0,0 @@
-// LzmaHandler.cpp
-
-#include "StdAfx.h"
-
-#include "LzmaHandler.h"
-
-#include "Common/Defs.h"
-#include "Common/StringConvert.h"
-#include "Common/ComTry.h"
-#include "Common/IntToString.h"
-
-#include "Windows/PropVariant.h"
-
-#include "../../Common/ProgressUtils.h"
-#include "../../Common/StreamUtils.h"
-#include "../Common/DummyOutStream.h"
-
-#include "LzmaFiltersDecode.h"
-
-namespace NArchive {
-namespace NLzma {
-
-STATPROPSTG kProps[] =
-{
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
- { NULL, kpidMethod, VT_UI1}
-};
-
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
-
-STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
-{
- *numItems = 1;
- return S_OK;
-}
-
-static void ConvertUInt32ToString(UInt32 value, wchar_t *s)
-{
- ConvertUInt64ToString(value, s + MyStringLen(s));
-}
-
-static void DictSizeToString(UInt32 value, wchar_t *s)
-{
- for (int i = 0; i <= 31; i++)
- if ((UInt32(1) << i) == value)
- {
- ConvertUInt32ToString(i, s);
- return;
- }
- wchar_t c = L'b';
- if ((value & ((1 << 20) - 1)) == 0)
- {
- value >>= 20;
- c = L'm';
- }
- else if ((value & ((1 << 10) - 1)) == 0)
- {
- value >>= 10;
- c = L'k';
- }
- ConvertUInt32ToString(value, s);
- int p = MyStringLen(s);
- s[p++] = c;
- s[p++] = L'\0';
-}
-
-static void MyStrCat(wchar_t *d, const wchar_t *s)
-{
- MyStringCopy(d + MyStringLen(d), s);
-}
-
-STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
-{
- if (index != 0)
- return E_INVALIDARG;
- NWindows::NCOM::CPropVariant propVariant;
- switch(propID)
- {
- case kpidSize:
- if (m_StreamInfo.HasUnpackSize())
- propVariant = (UInt64)m_StreamInfo.UnpackSize;
- break;
- case kpidPackSize:
- propVariant = (UInt64)m_PackSize;
- break;
- case kpidMethod:
- {
- wchar_t s[64];
- s[0] = '\0';
- if (m_StreamInfo.IsThereFilter)
- {
- const wchar_t *f;
- if (m_StreamInfo.FilterMethod == 0)
- f = L"Copy";
- else if (m_StreamInfo.FilterMethod == 1)
- f = L"BCJ";
- else
- f = L"Unknown";
- MyStrCat(s, f);
- MyStrCat(s, L" ");
- }
- MyStrCat(s, L"LZMA:");
- DictSizeToString(m_StreamInfo.GetDicSize(), s);
- propVariant = s;
- break;
- }
- }
- propVariant.Detach(value);
- return S_OK;
-}
-
-STDMETHODIMP CHandler::Open(IInStream *inStream,
- const UInt64 * /* maxCheckStartPosition */,
- IArchiveOpenCallback * /* openArchiveCallback */)
-{
- {
- RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_StreamStartPosition));
-
- HRESULT res = ReadStreamHeader(inStream, m_StreamInfo);
- if (res != S_OK)
- return S_FALSE;
-
- Byte b;
- RINOK(ReadStream_FALSE(inStream, &b, 1));
- if (b != 0)
- return S_FALSE;
-
- UInt64 endPos;
- RINOK(inStream->Seek(0, STREAM_SEEK_END, &endPos));
- m_PackSize = endPos - m_StreamStartPosition - m_StreamInfo.GetHeaderSize();
-
- m_Stream = inStream;
- }
- return S_OK;
-}
-
-STDMETHODIMP CHandler::Close()
-{
- m_Stream.Release();
- return S_OK;
-}
-
-
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
-{
- COM_TRY_BEGIN
- bool allFilesMode = (numItems == UInt32(-1));
- if (!allFilesMode)
- {
- if (numItems == 0)
- return S_OK;
- if (numItems != 1)
- return E_INVALIDARG;
- if (indices[0] != 0)
- return E_INVALIDARG;
- }
-
- bool testMode = (_aTestMode != 0);
-
- RINOK(extractCallback->SetTotal(m_PackSize));
-
- UInt64 currentTotalPacked = 0;
-
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
-
- {
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode = testMode ?
- NArchive::NExtract::NAskMode::kTest :
- NArchive::NExtract::NAskMode::kExtract;
-
- RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
-
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
- if(!testMode && !realOutStream)
- return S_OK;
- extractCallback->PrepareOperation(askMode);
- }
-
- CLocalProgress *lps = new CLocalProgress;
- CMyComPtr<ICompressProgressInfo> progress = lps;
- lps->Init(extractCallback, true);
-
- CDecoder decoder;
- RINOK(m_Stream->Seek(m_StreamStartPosition, STREAM_SEEK_SET, NULL));
- UInt64 streamPos = m_StreamStartPosition;
- Int32 opRes = NArchive::NExtract::NOperationResult::kOK;
- bool firstItem = true;
- for (;;)
- {
- CHeader st;
- HRESULT result = ReadStreamHeader(m_Stream, st);
- if (result != S_OK)
- {
- if (firstItem)
- return E_FAIL;
- break;
- }
- firstItem = false;
-
- lps->OutSize = outStreamSpec->GetSize();
- lps->InSize = currentTotalPacked;
- RINOK(lps->SetCur());
-
- streamPos += st.GetHeaderSize();
- UInt64 packProcessed;
-
- {
- result = decoder.Code(
- EXTERNAL_CODECS_VARS
- st, m_Stream, outStream, &packProcessed, progress);
- if (result == E_NOTIMPL)
- {
- opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
- break;
- }
- if (result == S_FALSE)
- {
- opRes = NArchive::NExtract::NOperationResult::kDataError;
- break;
- }
- RINOK(result);
- }
-
- if (packProcessed == (UInt64)(Int64)-1)
- break;
- RINOK(m_Stream->Seek(streamPos + packProcessed, STREAM_SEEK_SET, NULL));
- currentTotalPacked += packProcessed;
- streamPos += packProcessed;
- }
- outStream.Release();
- return extractCallback->SetOperationResult(opRes);
- COM_TRY_END
-}
-
-IMPL_ISetCompressCodecsInfo
-
-}}
diff --git a/CPP/7zip/Archive/Lzma/LzmaHandler.h b/CPP/7zip/Archive/Lzma/LzmaHandler.h
deleted file mode 100755
index e8fdcedc..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaHandler.h
+++ /dev/null
@@ -1,69 +0,0 @@
-// Lzma/Handler.h
-
-#ifndef __GZIP_HANDLER_H
-#define __GZIP_HANDLER_H
-
-#include "Common/MyCom.h"
-
-#include "../IArchive.h"
-#include "../../Common/CreateCoder.h"
-
-#include "LzmaIn.h"
-
-namespace NArchive {
-namespace NLzma {
-
-// const UInt64 k_LZMA = 0x030101;
-
-class CHandler:
- public IInArchive,
- PUBLIC_ISetCompressCodecsInfo
- public CMyUnknownImp
-{
-public:
- MY_QUERYINTERFACE_BEGIN
- MY_QUERYINTERFACE_ENTRY(IInArchive)
- QUERY_ENTRY_ISetCompressCodecsInfo
- MY_QUERYINTERFACE_END
- MY_ADDREF_RELEASE
-
- STDMETHOD(Open)(IInStream *inStream,
- const UInt64 *maxCheckStartPosition,
- IArchiveOpenCallback *openArchiveCallback);
- STDMETHOD(Close)();
-
- STDMETHOD(GetNumberOfItems)(UInt32 *numItems);
- STDMETHOD(GetProperty)(UInt32 index, PROPID propID, PROPVARIANT *value);
- STDMETHOD(Extract)(const UInt32* indices, UInt32 numItems,
- Int32 testMode, IArchiveExtractCallback *extractCallback);
-
- STDMETHOD(GetArchiveProperty)(PROPID propID, PROPVARIANT *value);
-
- STDMETHOD(GetNumberOfProperties)(UInt32 *numProperties);
- STDMETHOD(GetPropertyInfo)(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType);
-
- STDMETHOD(GetNumberOfArchiveProperties)(UInt32 *numProperties);
- STDMETHOD(GetArchivePropertyInfo)(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType);
-
- UString GetMethodString();
-public:
- CHandler() { }
-
-private:
- CHeader m_StreamInfo;
- UInt64 m_StreamStartPosition;
- UInt64 m_PackSize;
-
- CMyComPtr<IInStream> m_Stream;
-
- DECL_EXTERNAL_CODECS_VARS
-
- DECL_ISetCompressCodecsInfo
-
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzma/LzmaIn.cpp b/CPP/7zip/Archive/Lzma/LzmaIn.cpp
deleted file mode 100755
index 342b01e1..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaIn.cpp
+++ /dev/null
@@ -1,56 +0,0 @@
-// Archive/LzmaIn.cpp
-
-#include "StdAfx.h"
-
-#include "LzmaIn.h"
-
-#include "../../Common/StreamUtils.h"
-
-namespace NArchive {
-namespace NLzma {
-
-static bool CheckDictSize(const Byte *p)
-{
- UInt32 dicSize = GetUi32(p);
- int i;
- for (i = 1; i <= 30; i++)
- if (dicSize == ((UInt32)2 << i) || dicSize == ((UInt32)3 << i))
- return true;
- return false;
-}
-
-HRESULT ReadStreamHeader(ISequentialInStream *inStream, CHeader &block)
-{
- Byte sig[5 + 9];
- RINOK(ReadStream_FALSE(inStream, sig, 5 + 8));
-
- const Byte kMaxProp0Val = 5 * 5 * 9 - 1;
- if (sig[0] > kMaxProp0Val)
- return S_FALSE;
-
- for (int i = 0; i < 5; i++)
- block.LzmaProps[i] = sig[i];
-
- block.IsThereFilter = false;
- block.FilterMethod = 0;
-
- if (!CheckDictSize(sig + 1))
- {
- if (sig[0] > 1 || sig[1] > kMaxProp0Val)
- return S_FALSE;
- block.IsThereFilter = true;
- block.FilterMethod = sig[0];
- for (int i = 0; i < 5; i++)
- block.LzmaProps[i] = sig[i + 1];
- if (!CheckDictSize(block.LzmaProps + 1))
- return S_FALSE;
- RINOK(ReadStream_FALSE(inStream, sig + 5 + 8, 1));
- }
- UInt32 unpOffset = 5 + (block.IsThereFilter ? 1 : 0);
- block.UnpackSize = GetUi64(sig + unpOffset);
- if (block.HasUnpackSize() && block.UnpackSize >= ((UInt64)1 << 56))
- return S_FALSE;
- return S_OK;
-}
-
-}}
diff --git a/CPP/7zip/Archive/Lzma/LzmaIn.h b/CPP/7zip/Archive/Lzma/LzmaIn.h
deleted file mode 100755
index 6f237f2d..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaIn.h
+++ /dev/null
@@ -1,16 +0,0 @@
-// Archive/LzmaIn.h
-
-#ifndef __ARCHIVE_LZMA_IN_H
-#define __ARCHIVE_LZMA_IN_H
-
-#include "LzmaItem.h"
-#include "../../IStream.h"
-
-namespace NArchive {
-namespace NLzma {
-
-HRESULT ReadStreamHeader(ISequentialInStream *inStream, CHeader &st);
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzma/LzmaItem.h b/CPP/7zip/Archive/Lzma/LzmaItem.h
deleted file mode 100755
index 8fcae210..00000000
--- a/CPP/7zip/Archive/Lzma/LzmaItem.h
+++ /dev/null
@@ -1,27 +0,0 @@
-// Archive/LzmaItem.h
-
-#ifndef __ARCHIVE_LZMA_ITEM_H
-#define __ARCHIVE_LZMA_ITEM_H
-
-#include "Common/Types.h"
-
-#include "../../../../C/CpuArch.h"
-
-namespace NArchive {
-namespace NLzma {
-
-struct CHeader
-{
- UInt64 UnpackSize;
- bool IsThereFilter;
- Byte FilterMethod;
- Byte LzmaProps[5];
-
- UInt32 GetDicSize() const { return GetUi32(LzmaProps + 1); }
- bool HasUnpackSize() const { return (UnpackSize != (UInt64)(Int64)-1); }
- unsigned GetHeaderSize() const { return 5 + 8 + (IsThereFilter ? 1 : 0); }
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Lzma/StdAfx.h b/CPP/7zip/Archive/Lzma/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/Lzma/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/LzmaHandler.cpp b/CPP/7zip/Archive/LzmaHandler.cpp
new file mode 100755
index 00000000..5dd0aac7
--- /dev/null
+++ b/CPP/7zip/Archive/LzmaHandler.cpp
@@ -0,0 +1,436 @@
+// LzmaHandler.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/ComTry.h"
+#include "Common/IntToString.h"
+
+#include "Windows/PropVariant.h"
+
+#include "../Common/CreateCoder.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/LzmaDecoder.h"
+
+#include "Common/DummyOutStream.h"
+
+using namespace NWindows;
+
+namespace NArchive {
+namespace NLzma {
+
+static bool CheckDicSize(const Byte *p)
+{
+ UInt32 dicSize = GetUi32(p);
+ for (int i = 1; i <= 30; i++)
+ if (dicSize == ((UInt32)2 << i) || dicSize == ((UInt32)3 << i))
+ return true;
+ return (dicSize == 0xFFFFFFFF);
+}
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMethod, VT_BSTR}
+};
+
+struct CHeader
+{
+ UInt64 Size;
+ Byte FilterID;
+ Byte LzmaProps[5];
+
+ UInt32 GetDicSize() const { return GetUi32(LzmaProps + 1); }
+ bool HasSize() const { return (Size != (UInt64)(Int64)-1); }
+ bool Parse(const Byte *buf, bool isThereFilter);
+};
+
+bool CHeader::Parse(const Byte *buf, bool isThereFilter)
+{
+ FilterID = 0;
+ if (isThereFilter)
+ FilterID = buf[0];
+ const Byte *sig = buf + (isThereFilter ? 1 : 0);
+ for (int i = 0; i < 5; i++)
+ LzmaProps[i] = sig[i];
+ Size = GetUi64(sig + 5);
+ return
+ LzmaProps[0] < 5 * 5 * 9 &&
+ FilterID < 2 &&
+ (!HasSize() || Size < ((UInt64)1 << 56)) &&
+ CheckDicSize(LzmaProps + 1);
+}
+
+class CDecoder
+{
+ NCompress::NLzma::CDecoder *_lzmaDecoderSpec;
+ CMyComPtr<ICompressCoder> _lzmaDecoder;
+ CMyComPtr<ISequentialOutStream> _bcjStream;
+public:
+ ~CDecoder();
+ HRESULT Create(DECL_EXTERNAL_CODECS_LOC_VARS
+ bool filtered, ISequentialInStream *inStream);
+
+ HRESULT Code(const CHeader &header, ISequentialOutStream *outStream, ICompressProgressInfo *progress);
+
+ UInt64 GetInputProcessedSize() const { return _lzmaDecoderSpec->GetInputProcessedSize(); }
+
+ void ReleaseInStream() { if (_lzmaDecoder) _lzmaDecoderSpec->ReleaseInStream(); }
+
+ HRESULT ReadInput(Byte *data, UInt32 size, UInt32 *processedSize)
+ { return _lzmaDecoderSpec->ReadFromInputStream(data, size, processedSize); }
+};
+
+static const UInt64 k_BCJ = 0x03030103;
+
+HRESULT CDecoder::Create(
+ DECL_EXTERNAL_CODECS_LOC_VARS
+ bool filteredMode, ISequentialInStream *inStream)
+{
+ if (!_lzmaDecoder)
+ {
+ _lzmaDecoderSpec = new NCompress::NLzma::CDecoder;
+ _lzmaDecoder = _lzmaDecoderSpec;
+ }
+
+ if (filteredMode)
+ {
+ if (!_bcjStream)
+ {
+ CMyComPtr<ICompressCoder> coder;
+ RINOK(CreateCoder(EXTERNAL_CODECS_LOC_VARS k_BCJ, coder, false));
+ if (!coder)
+ return E_NOTIMPL;
+ coder.QueryInterface(IID_ISequentialOutStream, &_bcjStream);
+ if (!_bcjStream)
+ return E_NOTIMPL;
+ }
+ }
+
+ return _lzmaDecoderSpec->SetInStream(inStream);
+}
+
+CDecoder::~CDecoder()
+{
+ ReleaseInStream();
+}
+
+HRESULT CDecoder::Code(const CHeader &header, ISequentialOutStream *outStream,
+ ICompressProgressInfo *progress)
+{
+ if (header.FilterID > 1)
+ return E_NOTIMPL;
+
+ {
+ CMyComPtr<ICompressSetDecoderProperties2> setDecoderProperties;
+ _lzmaDecoder.QueryInterface(IID_ICompressSetDecoderProperties2, &setDecoderProperties);
+ if (!setDecoderProperties)
+ return E_NOTIMPL;
+ RINOK(setDecoderProperties->SetDecoderProperties2(header.LzmaProps, 5));
+ }
+
+ CMyComPtr<ICompressSetOutStream> setOutStream;
+
+ bool filteredMode = (header.FilterID == 1);
+
+ if (filteredMode)
+ {
+ _bcjStream.QueryInterface(IID_ICompressSetOutStream, &setOutStream);
+ if (!setOutStream)
+ return E_NOTIMPL;
+ RINOK(setOutStream->SetOutStream(outStream));
+ outStream = _bcjStream;
+ }
+
+ const UInt64 *Size = header.HasSize() ? &header.Size : NULL;
+ HRESULT res = _lzmaDecoderSpec->CodeResume(outStream, Size, progress);
+
+ if (filteredMode)
+ {
+ CMyComPtr<IOutStreamFlush> flush;
+ _bcjStream.QueryInterface(IID_IOutStreamFlush, &flush);
+ if (flush)
+ {
+ HRESULT res2 = flush->Flush();
+ if (res == S_OK)
+ res = res2;
+ }
+ HRESULT res2 = setOutStream->ReleaseOutStream();
+ if (res == S_OK)
+ res = res2;
+ }
+ RINOK(res);
+
+ return S_OK;
+}
+
+
+class CHandler:
+ public IInArchive,
+ public IArchiveOpenSeq,
+ PUBLIC_ISetCompressCodecsInfo
+ public CMyUnknownImp
+{
+ CHeader _header;
+ bool _lzma86;
+ UInt64 _startPosition;
+ UInt64 _packSize;
+ bool _packSizeDefined;
+ CMyComPtr<IInStream> _stream;
+ CMyComPtr<ISequentialInStream> _seqStream;
+
+ DECL_EXTERNAL_CODECS_VARS
+ DECL_ISetCompressCodecsInfo
+
+public:
+ MY_QUERYINTERFACE_BEGIN
+ MY_QUERYINTERFACE_ENTRY(IInArchive)
+ MY_QUERYINTERFACE_ENTRY(IArchiveOpenSeq)
+ QUERY_ENTRY_ISetCompressCodecsInfo
+ MY_QUERYINTERFACE_END
+ MY_ADDREF_RELEASE
+
+ INTERFACE_IInArchive(;)
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream);
+
+ CHandler(bool lzma86) { _lzma86 = lzma86; }
+
+ unsigned GetHeaderSize() const { return 5 + 8 + (_lzma86 ? 1 : 0); }
+
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPhySize: if (_packSizeDefined) prop = _packSize; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = 1;
+ return S_OK;
+}
+
+static void DictSizeToString(UInt32 value, char *s)
+{
+ for (int i = 0; i <= 31; i++)
+ if ((UInt32(1) << i) == value)
+ {
+ ::ConvertUInt32ToString(i, s);
+ return;
+ }
+ char c = 'b';
+ if ((value & ((1 << 20) - 1)) == 0)
+ {
+ value >>= 20;
+ c = 'm';
+ }
+ else if ((value & ((1 << 10) - 1)) == 0)
+ {
+ value >>= 10;
+ c = 'k';
+ }
+ ::ConvertUInt32ToString(value, s);
+ int p = MyStringLen(s);
+ s[p++] = c;
+ s[p++] = '\0';
+}
+
+static void MyStrCat(char *d, const char *s)
+{
+ MyStringCopy(d + MyStringLen(d), s);
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidSize: if (_stream && _header.HasSize()) prop = _header.Size; break;
+ case kpidPackSize: if (_packSizeDefined) prop = _packSize; break;
+ case kpidMethod:
+ if (_stream)
+ {
+ char s[64];
+ s[0] = '\0';
+ if (_header.FilterID != 0)
+ MyStrCat(s, "BCJ ");
+ MyStrCat(s, "LZMA:");
+ DictSizeToString(_header.GetDicSize(), s + MyStringLen(s));
+ prop = s;
+ }
+ break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Open(IInStream *inStream, const UInt64 *, IArchiveOpenCallback *)
+{
+ RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &_startPosition));
+
+ const UInt32 kBufSize = 1 + 5 + 8 + 1;
+ Byte buf[kBufSize];
+
+ RINOK(ReadStream_FALSE(inStream, buf, kBufSize));
+
+ if (!_header.Parse(buf, _lzma86))
+ return S_FALSE;
+ const Byte *start = buf + GetHeaderSize();
+ if (start[0] != 0)
+ return S_FALSE;
+
+ UInt64 endPos;
+ RINOK(inStream->Seek(0, STREAM_SEEK_END, &endPos));
+ _packSize = endPos - _startPosition;
+ _packSizeDefined = true;
+
+ _stream = inStream;
+ _seqStream = inStream;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::OpenSeq(ISequentialInStream *stream)
+{
+ Close();
+ _seqStream = stream;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _packSizeDefined = false;
+ _stream.Release();
+ _seqStream.Release();
+ return S_OK;
+}
+
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool allFilesMode = (numItems == (UInt32)-1);
+ if (!allFilesMode)
+ {
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
+ }
+
+ bool testMode = (_aTestMode != 0);
+ if (_stream)
+ extractCallback->SetTotal(_packSize);
+
+
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
+ if (!testMode && !realOutStream)
+ return S_OK;
+
+ extractCallback->PrepareOperation(askMode);
+
+ CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+ outStreamSpec->SetStream(realOutStream);
+ outStreamSpec->Init();
+ realOutStream.Release();
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, true);
+
+ if (_stream)
+ {
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ }
+
+ CDecoder decoder;
+ HRESULT result = decoder.Create(
+ EXTERNAL_CODECS_VARS
+ _lzma86, _seqStream);
+ RINOK(result);
+
+ Int32 opRes = NArchive::NExtract::NOperationResult::kOK;
+ bool firstItem = true;
+
+ for (;;)
+ {
+ lps->OutSize = outStreamSpec->GetSize();
+ lps->InSize = _packSize = decoder.GetInputProcessedSize();
+ _packSizeDefined = true;
+ RINOK(lps->SetCur());
+
+ CHeader st;
+
+ const UInt32 kBufSize = 1 + 5 + 8;
+ Byte buf[kBufSize];
+ const UInt32 headerSize = GetHeaderSize();
+ UInt32 processed;
+ RINOK(decoder.ReadInput(buf, headerSize, &processed));
+ if (processed != headerSize)
+ break;
+
+ if (!st.Parse(buf, _lzma86))
+ break;
+ firstItem = false;
+
+ result = decoder.Code(st, outStream, progress);
+ if (result == E_NOTIMPL)
+ {
+ opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
+ break;
+ }
+ if (result == S_FALSE)
+ {
+ opRes = NArchive::NExtract::NOperationResult::kDataError;
+ break;
+ }
+ RINOK(result);
+ }
+ if (firstItem)
+ return E_FAIL;
+ outStream.Release();
+ return extractCallback->SetOperationResult(opRes);
+ COM_TRY_END
+}
+
+IMPL_ISetCompressCodecsInfo
+
+static IInArchive *CreateArc() { return new CHandler(false); }
+static IInArchive *CreateArc86() { return new CHandler(true); }
+
+namespace NLzmaAr {
+
+static CArcInfo g_ArcInfo =
+ { L"lzma", L"lzma", 0, 0xA, { 0 }, 0, true, CreateArc, NULL };
+REGISTER_ARC(Lzma)
+
+}
+
+namespace NLzma86Ar {
+
+static CArcInfo g_ArcInfo =
+ { L"lzma86", L"lzma86", 0, 0xB, { 0 }, 0, true, CreateArc86, NULL };
+REGISTER_ARC(Lzma86)
+
+}
+
+}}
diff --git a/CPP/7zip/Archive/MachoHandler.cpp b/CPP/7zip/Archive/MachoHandler.cpp
index 76f63a21..342a8e76 100755
--- a/CPP/7zip/Archive/MachoHandler.cpp
+++ b/CPP/7zip/Archive/MachoHandler.cpp
@@ -16,8 +16,6 @@
#include "../Compress/CopyCoder.h"
-#include "Common/DummyOutStream.h"
-
static UInt32 Get32(const Byte *p, int be) { if (be) return GetBe32(p); return GetUi32(p); }
static UInt64 Get64(const Byte *p, int be) { if (be) return GetBe64(p); return GetUi64(p); }
@@ -35,8 +33,8 @@ namespace NMacho {
#define MACH_MACHINE_PPC64 (MACH_ARCH_ABI64 | MACH_MACHINE_PPC)
#define MACH_MACHINE_AMD64 (MACH_ARCH_ABI64 | MACH_MACHINE_386)
-#define MACH_CMD_SEGMENT_32 1
-#define MACH_CMD_SEGMENT_64 0x19
+#define MACH_CMD_SEGMENT_32 1
+#define MACH_CMD_SEGMENT_64 0x19
#define MACH_SECT_TYPE_MASK 0x000000FF
#define MACH_SECT_ATTR_MASK 0xFFFFFF00
@@ -427,22 +425,10 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(extractCallback, false);
-
-
-
-
-
-
-
-
-
CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
CMyComPtr<ISequentialInStream> inStream(streamSpec);
streamSpec->SetStream(_inStream);
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
-
for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
{
lps->InSize = lps->OutSize = currentTotalSize;
@@ -453,24 +439,19 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
UInt32 index = allFilesMode ? i : indices[i];
const CSection &item = _sections[index];
currentItemSize = item.GetPackSize();
- {
- CMyComPtr<ISequentialOutStream> realOutStream;
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- if (!testMode && (!realOutStream))
- continue;
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
- }
+
+ CMyComPtr<ISequentialOutStream> outStream;
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
+ if (!testMode && !outStream)
+ continue;
RINOK(extractCallback->PrepareOperation(askMode));
RINOK(_inStream->Seek(item.Pa, STREAM_SEEK_SET, NULL));
streamSpec->Init(currentItemSize);
RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
- outStreamSpec->ReleaseStream();
- RINOK(extractCallback->SetOperationResult((copyCoderSpec->TotalSize == currentItemSize) ?
-
+ outStream.Release();
+ RINOK(extractCallback->SetOperationResult(copyCoderSpec->TotalSize == currentItemSize ?
NArchive::NExtract::NOperationResult::kOK:
-
NArchive::NExtract::NOperationResult::kDataError));
}
return S_OK;
@@ -485,4 +466,3 @@ static CArcInfo g_ArcInfo =
REGISTER_ARC(Macho)
}}
- \ No newline at end of file
diff --git a/CPP/7zip/Archive/MbrHandler.cpp b/CPP/7zip/Archive/MbrHandler.cpp
new file mode 100755
index 00000000..47b18f15
--- /dev/null
+++ b/CPP/7zip/Archive/MbrHandler.cpp
@@ -0,0 +1,508 @@
+// MbrHandler.cpp
+
+#include "StdAfx.h"
+
+// #define SHOW_DEBUG_INFO
+
+#ifdef SHOW_DEBUG_INFO
+#include <stdio.h>
+#endif
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/Buffer.h"
+#include "Common/ComTry.h"
+#include "Common/IntToString.h"
+#include "Common/MyString.h"
+
+#include "Windows/PropVariant.h"
+
+#include "../Common/LimitedStreams.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#ifdef SHOW_DEBUG_INFO
+#define PRF(x) x
+#else
+#define PRF(x)
+#endif
+
+using namespace NWindows;
+
+namespace NArchive {
+namespace NMbr {
+
+struct CChs
+{
+ Byte Head;
+ Byte SectCyl;
+ Byte Cyl8;
+
+ UInt32 GetSector() const { return SectCyl & 0x3F; }
+ UInt32 GetCyl() const { return ((UInt32)SectCyl >> 6 << 8) | Cyl8; }
+ void ToString(NCOM::CPropVariant &prop) const;
+
+ void Parse(const Byte *p)
+ {
+ Head = p[0];
+ SectCyl = p[1];
+ Cyl8 = p[2];
+ }
+ bool Check() const { return GetSector() > 0; }
+};
+
+#define RINOZ(x) { int __tt = (x); if (__tt != 0) return __tt; }
+
+static int CompareChs(const CChs &c1, const CChs &c2)
+{
+ RINOZ(MyCompare(c1.GetCyl(), c2.GetCyl()));
+ RINOZ(MyCompare(c1.Head, c2.Head));
+ return MyCompare(c1.GetSector(), c2.GetSector());
+}
+
+static void AddUIntToString(UInt32 val, AString &res)
+{
+ char s[16];
+ ConvertUInt32ToString(val, s);
+ res += s;
+}
+
+void CChs::ToString(NCOM::CPropVariant &prop) const
+{
+ AString s;
+ AddUIntToString(GetCyl(), s);
+ s += '-';
+ AddUIntToString(Head, s);
+ s += '-';
+ AddUIntToString(GetSector(), s);
+ prop = s;
+}
+
+struct CPartition
+{
+ Byte Status;
+ CChs BeginChs;
+ Byte Type;
+ CChs EndChs;
+ UInt32 Lba;
+ UInt32 NumBlocks;
+
+ CPartition() { memset (this, 0, sizeof(*this)); }
+
+ bool IsEmpty() const { return Type == 0; }
+ bool IsExtended() const { return Type == 5 || Type == 0xF; }
+ UInt32 GetLimit() const { return Lba + NumBlocks; }
+ // bool IsActive() const { return Status == 0x80; }
+ UInt64 GetPos() const { return (UInt64)Lba * 512; }
+ UInt64 GetSize() const { return (UInt64)NumBlocks * 512; }
+
+ bool CheckLbaLimits() const { return (UInt32)0xFFFFFFFF - Lba >= NumBlocks; }
+ bool Parse(const Byte *p)
+ {
+ Status = p[0];
+ BeginChs.Parse(p + 1);
+ Type = p[4];
+ EndChs.Parse(p + 5);
+ Lba = GetUi32(p + 8);
+ NumBlocks = GetUi32(p + 12);
+ if (Type == 0)
+ return true;
+ if (Status != 0 && Status != 0x80)
+ return false;
+ return
+ BeginChs.Check() &&
+ EndChs.Check() &&
+ CompareChs(BeginChs, EndChs) <= 0 &&
+ NumBlocks > 0 &&
+ CheckLbaLimits();
+ }
+
+ #ifdef SHOW_DEBUG_INFO
+ void Print() const
+ {
+ NCOM::CPropVariant prop, prop2;
+ BeginChs.ToString(prop);
+ EndChs.ToString(prop2);
+ printf(" %2x %2x %8X %8X %12S %12S", (int)Status, (int)Type, Lba, NumBlocks, prop.bstrVal, prop2.bstrVal);
+ }
+ #endif
+};
+
+struct CPartType
+{
+ UInt32 Id;
+ const char *Ext;
+ const char *Name;
+};
+
+static const char *kFat = "fat";
+
+static const CPartType kPartTypes[] =
+{
+ { 0x01, kFat, "FAT12" },
+ { 0x04, kFat, "FAT16 DOS 3.0+" },
+ { 0x05, 0, "Extended" },
+ { 0x06, kFat, "FAT16 DOS 3.31+" },
+ { 0x07, "ntfs", "NTFS" },
+ { 0x0B, kFat, "FAT32" },
+ { 0x0C, kFat, "FAT32-LBA" },
+ { 0x0E, kFat, "FAT16-LBA" },
+ { 0x0F, 0, "Extended-LBA" },
+ { 0x11, kFat, "FAT12-Hidden" },
+ { 0x14, kFat, "FAT16-Hidden < 32 MB" },
+ { 0x16, kFat, "FAT16-Hidden >= 32 MB" },
+ { 0x1B, kFat, "FAT32-Hidden" },
+ { 0x1C, kFat, "FAT32-LBA-Hidden" },
+ { 0x1E, kFat, "FAT16-LBA-WIN95-Hidden" },
+ { 0x82, 0, "Solaris x86 / Linux swap" },
+ { 0x83, 0, "Linux" },
+ { 0xBE, 0, "Solaris 8 boot" },
+ { 0xBF, 0, "New Solaris x86" },
+ { 0xC2, 0, "Linux-Hidden" },
+ { 0xC3, 0, "Linux swap-Hidden" },
+ { 0xEE, 0, "EFI-MBR" },
+ { 0xEE, 0, "EFI" }
+};
+
+static int FindPartType(UInt32 type)
+{
+ for (int i = 0; i < sizeof(kPartTypes) / sizeof(kPartTypes[0]); i++)
+ if (kPartTypes[i].Id == type)
+ return i;
+ return -1;
+}
+
+struct CItem
+{
+ bool IsReal;
+ bool IsPrim;
+ UInt64 Size;
+ CPartition Part;
+};
+
+class CHandler:
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp
+{
+ CMyComPtr<IInStream> _stream;
+ CObjectVector<CItem> _items;
+ UInt64 _totalSize;
+ CByteBuffer _buffer;
+
+ HRESULT ReadTables(IInStream *stream, UInt32 baseLba, UInt32 lba, int level);
+public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+};
+
+HRESULT CHandler::ReadTables(IInStream *stream, UInt32 baseLba, UInt32 lba, int level)
+{
+ if (level >= 128 || _items.Size() >= 128)
+ return S_FALSE;
+
+ const int kNumHeaderParts = 4;
+ CPartition parts[kNumHeaderParts];
+
+ {
+ const UInt32 kSectorSize = 512;
+ _buffer.SetCapacity(kSectorSize);
+ Byte *buf = _buffer;
+ UInt64 newPos = (UInt64)lba << 9;
+ if (newPos + 512 > _totalSize)
+ return S_FALSE;
+ RINOK(stream->Seek(newPos, STREAM_SEEK_SET, NULL));
+ RINOK(ReadStream_FALSE(stream, buf, kSectorSize));
+
+ if (buf[0x1FE] != 0x55 || buf[0x1FF] != 0xAA)
+ return S_FALSE;
+
+ for (int i = 0; i < kNumHeaderParts; i++)
+ if (!parts[i].Parse(buf + 0x1BE + 16 * i))
+ return S_FALSE;
+ }
+
+ PRF(printf("\n# %8X", lba));
+
+ UInt32 limLba = lba + 1;
+ if (limLba == 0)
+ return S_FALSE;
+
+ for (int i = 0; i < kNumHeaderParts; i++)
+ {
+ CPartition &part = parts[i];
+
+ if (part.IsEmpty())
+ continue;
+ PRF(printf("\n %2d ", (int)level));
+ #ifdef SHOW_DEBUG_INFO
+ part.Print();
+ #endif
+
+ int numItems = _items.Size();
+ UInt32 newLba = lba + part.Lba;
+
+ if (part.IsExtended())
+ {
+ // if (part.Type == 5) // Check it!
+ newLba = baseLba + part.Lba;
+ if (newLba < limLba)
+ return S_FALSE;
+ HRESULT res = ReadTables(stream, level < 1 ? newLba : baseLba, newLba, level + 1);
+ if (res != S_FALSE && res != S_OK)
+ return res;
+ }
+ if (newLba < limLba)
+ return S_FALSE;
+ part.Lba = newLba;
+ if (!part.CheckLbaLimits())
+ return S_FALSE;
+
+ CItem n;
+ n.Part = part;
+ bool addItem = false;
+ if (numItems == _items.Size())
+ {
+ n.IsPrim = (level == 0);
+ n.IsReal = true;
+ addItem = true;
+ }
+ else
+ {
+ const CItem &back = _items.Back();
+ UInt32 backLimit = back.Part.GetLimit();
+ UInt32 partLimit = part.GetLimit();
+ if (backLimit < partLimit)
+ {
+ n.IsReal = false;
+ n.Part.Lba = backLimit;
+ n.Part.NumBlocks = partLimit - backLimit;
+ addItem = true;
+ }
+ }
+ if (addItem)
+ {
+ if (n.Part.GetLimit() < limLba)
+ return S_FALSE;
+ limLba = n.Part.GetLimit();
+ n.Size = n.Part.GetSize();
+ _items.Add(n);
+ }
+ }
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream,
+ const UInt64 * /* maxCheckStartPosition */,
+ IArchiveOpenCallback * /* openArchiveCallback */)
+{
+ COM_TRY_BEGIN
+ Close();
+ RINOK(stream->Seek(0, STREAM_SEEK_END, &_totalSize));
+ RINOK(ReadTables(stream, 0, 0, 0));
+ if (_items.IsEmpty())
+ return S_FALSE;
+ UInt32 lbaLimit = _items.Back().Part.GetLimit();
+ UInt64 lim = (UInt64)lbaLimit << 9;
+ if (lim < _totalSize)
+ {
+ CItem n;
+ n.Part.Lba = lbaLimit;
+ n.Size = _totalSize - lim;
+ n.IsReal = false;
+ _items.Add(n);
+ }
+ _stream = stream;
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _items.Clear();
+ _stream.Release();
+ return S_OK;
+}
+
+enum
+{
+ kpidPrimary = kpidUserDefined,
+ kpidBegChs,
+ kpidEndChs,
+};
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidFileSystem, VT_BSTR},
+ { NULL, kpidOffset, VT_UI8},
+ { L"Primary", kpidPrimary, VT_BOOL},
+ { L"Begin CHS", kpidBegChs, VT_BSTR},
+ { L"End CHS", kpidEndChs, VT_BSTR}
+};
+
+IMP_IInArchive_Props_WITH_NAME
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidMainSubfile:
+ {
+ int mainIndex = -1;
+ for (int i = 0; i < _items.Size(); i++)
+ if (_items[i].IsReal)
+ {
+ if (mainIndex >= 0)
+ {
+ mainIndex = -1;
+ break;
+ }
+ mainIndex = i;
+ }
+ if (mainIndex >= 0)
+ prop = (UInt32)mainIndex;
+ break;
+ }
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = _items.Size();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NCOM::CPropVariant prop;
+
+ const CItem &item = _items[index];
+ const CPartition &part = item.Part;
+ switch(propID)
+ {
+ case kpidPath:
+ {
+ AString s;
+ AddUIntToString(index, s);
+ if (item.IsReal)
+ {
+ int typeIndex = FindPartType(part.Type);
+ s += '.';
+ const char *ext = "img";
+ if (typeIndex >= 0 && kPartTypes[typeIndex].Ext != 0)
+ ext = kPartTypes[typeIndex].Ext;
+ s += ext;
+ }
+ prop = s;
+ break;
+ }
+ case kpidFileSystem:
+ if (item.IsReal)
+ {
+ char s[32];
+ ConvertUInt32ToString(part.Type, s);
+ const char *res = s;
+ int typeIndex = FindPartType(part.Type);
+ if (typeIndex >= 0 && kPartTypes[typeIndex].Name)
+ res = kPartTypes[typeIndex].Name;
+ prop = res;
+ }
+ break;
+ case kpidSize: prop = item.Size; break;;
+ case kpidPackSize: prop = item.Size; break;
+ case kpidOffset: prop = part.GetPos(); break;
+ case kpidPrimary: if (item.IsReal) prop = item.IsPrim; break;
+ case kpidBegChs: if (item.IsReal) part.BeginChs.ToString(prop); break;
+ case kpidEndChs: if (item.IsReal) part.EndChs.ToString(prop); break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool testMode = (_aTestMode != 0);
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (allFilesMode)
+ numItems = _items.Size();
+ if (numItems == 0)
+ return S_OK;
+ UInt64 totalSize = 0;
+ UInt32 i;
+ for (i = 0; i < numItems; i++)
+ totalSize += _items[allFilesMode ? i : indices[i]].Size;
+ extractCallback->SetTotal(totalSize);
+
+ totalSize = 0;
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
+ CMyComPtr<ISequentialInStream> inStream(streamSpec);
+ streamSpec->SetStream(_stream);
+
+ for (i = 0; i < numItems; i++)
+ {
+ lps->InSize = totalSize;
+ lps->OutSize = totalSize;
+ RINOK(lps->SetCur());
+ CMyComPtr<ISequentialOutStream> outStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ Int32 index = allFilesMode ? i : indices[i];
+ const CItem &item = _items[index];
+ const CPartition &part = item.Part;
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
+ totalSize += item.Size;
+ if (!testMode && (!outStream))
+ continue;
+ RINOK(extractCallback->PrepareOperation(askMode));
+
+ RINOK(_stream->Seek(part.GetPos(), STREAM_SEEK_SET, NULL));
+ streamSpec->Init(item.Size);
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ outStream.Release();
+ RINOK(extractCallback->SetOperationResult(copyCoderSpec->TotalSize == item.Size ?
+ NArchive::NExtract::NOperationResult::kOK:
+ NArchive::NExtract::NOperationResult::kDataError));
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ const CItem &item = _items[index];
+ return CreateLimitedInStream(_stream, item.Part.GetPos(), item.Size, stream);
+ COM_TRY_END
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"MBR", L"mbr", 0, 0xDB, { 1, 1, 0 }, 3, false, CreateArc, 0 };
+
+REGISTER_ARC(Mbr)
+
+}}
diff --git a/CPP/7zip/Archive/MubHandler.cpp b/CPP/7zip/Archive/MubHandler.cpp
index 25c3815e..f099aad2 100755
--- a/CPP/7zip/Archive/MubHandler.cpp
+++ b/CPP/7zip/Archive/MubHandler.cpp
@@ -34,22 +34,23 @@ const UInt32 kNumFilesMax = 10;
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
UInt64 _startPos;
- CMyComPtr<IInStream> _inStream;
+ CMyComPtr<IInStream> _stream;
UInt32 _numItems;
CItem _items[kNumFilesMax + 1];
HRESULT Open2(IInStream *stream);
public:
- MY_UNKNOWN_IMP1(IInArchive)
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
STATPROPSTG kProps[] =
{
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8}
+ { NULL, kpidSize, VT_UI8}
};
IMP_IInArchive_Props
@@ -166,7 +167,7 @@ STDMETHODIMP CHandler::Open(IInStream *inStream,
{
if (Open2(inStream) != S_OK)
return S_FALSE;
- _inStream = inStream;
+ _stream = inStream;
}
catch(...) { return S_FALSE; }
return S_OK;
@@ -175,7 +176,7 @@ STDMETHODIMP CHandler::Open(IInStream *inStream,
STDMETHODIMP CHandler::Close()
{
- _inStream.Release();
+ _stream.Release();
_numItems = 0;
return S_OK;
}
@@ -203,7 +204,6 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
extractCallback->SetTotal(totalSize);
UInt64 currentTotalSize = 0;
- UInt64 currentItemSize;
NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
@@ -214,9 +214,9 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_inStream);
+ streamSpec->SetStream(_stream);
- for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
+ for (i = 0; i < numItems; i++)
{
lps->InSize = lps->OutSize = currentTotalSize;
RINOK(lps->SetCur());
@@ -227,12 +227,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
UInt32 index = allFilesMode ? i : indices[i];
const CItem &item = _items[index];
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- currentItemSize = item.Size;
-
-
-
-
-
+ currentTotalSize += item.Size;
if (!testMode && (!realOutStream))
continue;
@@ -242,7 +237,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
continue;
}
- RINOK(_inStream->Seek(_startPos + item.Offset, STREAM_SEEK_SET, NULL));
+ RINOK(_stream->Seek(_startPos + item.Offset, STREAM_SEEK_SET, NULL));
streamSpec->Init(item.Size);
RINOK(copyCoder->Code(inStream, realOutStream, NULL, NULL, progress));
realOutStream.Release();
@@ -254,6 +249,14 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
COM_TRY_END
}
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ const CItem &item = _items[index];
+ return CreateLimitedInStream(_stream, _startPos + item.Offset, item.Size, stream);
+ COM_TRY_END
+}
+
static IInArchive *CreateArc() { return new CHandler; }
static CArcInfo g_ArcInfo =
diff --git a/CPP/7zip/Archive/NtfsHandler.cpp b/CPP/7zip/Archive/NtfsHandler.cpp
new file mode 100755
index 00000000..37847a24
--- /dev/null
+++ b/CPP/7zip/Archive/NtfsHandler.cpp
@@ -0,0 +1,1725 @@
+// NtfsHandler.cpp
+
+#include "StdAfx.h"
+
+// #define SHOW_DEBUG_INFO
+// #define SHOW_DEBUG_INFO2
+
+#if defined(SHOW_DEBUG_INFO) || defined(SHOW_DEBUG_INFO2)
+#include <stdio.h>
+#endif
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/Buffer.h"
+#include "Common/ComTry.h"
+#include "Common/IntToString.h"
+#include "Common/MyCom.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/PropVariant.h"
+#include "Windows/Time.h"
+
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#include "Common/DummyOutStream.h"
+
+#ifdef SHOW_DEBUG_INFO
+#define PRF(x) x
+#else
+#define PRF(x)
+#endif
+
+#ifdef SHOW_DEBUG_INFO2
+#define PRF2(x) x
+#else
+#define PRF2(x)
+#endif
+
+#define Get16(p) GetUi16(p)
+#define Get32(p) GetUi32(p)
+#define Get64(p) GetUi64(p)
+
+#define G16(p, dest) dest = Get16(p);
+#define G32(p, dest) dest = Get32(p);
+#define G64(p, dest) dest = Get64(p);
+
+namespace NArchive {
+namespace Ntfs {
+
+static const UInt32 kNumSysRecs = 16;
+static const UInt32 kRecIndex_Volume = 3;
+static const UInt32 kRecIndex_BadClus = 8;
+
+struct CHeader
+{
+ Byte SectorSizeLog;
+ Byte ClusterSizeLog;
+ // Byte MediaType;
+ UInt32 NumHiddenSectors;
+ UInt64 NumClusters;
+ UInt64 MftCluster;
+ UInt64 SerialNumber;
+ UInt16 SectorsPerTrack;
+ UInt16 NumHeads;
+
+ UInt64 GetPhySize() const { return NumClusters << ClusterSizeLog; }
+ UInt32 ClusterSize() const { return (UInt32)1 << ClusterSizeLog; }
+ bool Parse(const Byte *p);
+};
+
+static int GetLog(UInt32 num)
+{
+ for (int i = 0; i < 31; i++)
+ if (((UInt32)1 << i) == num)
+ return i;
+ return -1;
+}
+
+bool CHeader::Parse(const Byte *p)
+{
+ if (p[0x1FE] != 0x55 || p[0x1FF] != 0xAA)
+ return false;
+
+ int codeOffset = 0;
+ switch (p[0])
+ {
+ case 0xE9: codeOffset = 3 + (Int16)Get16(p + 1); break;
+ case 0xEB: if (p[2] != 0x90) return false; codeOffset = 2 + (signed char)p[1]; break;
+ default: return false;
+ }
+ Byte sectorsPerClusterLog;
+
+ if (memcmp(p + 3, "NTFS ", 8) != 0)
+ return false;
+ {
+ int s = GetLog(Get16(p + 11));
+ if (s < 9 || s > 12)
+ return false;
+ SectorSizeLog = (Byte)s;
+ s = GetLog(p[13]);
+ if (s < 0)
+ return false;
+ sectorsPerClusterLog = (Byte)s;
+ ClusterSizeLog = SectorSizeLog + sectorsPerClusterLog;
+ }
+
+ for (int i = 14; i < 21; i++)
+ if (p[i] != 0)
+ return false;
+
+ // MediaType = p[21];
+ if (Get16(p + 22) != 0) // NumFatSectors
+ return false;
+ G16(p + 24, SectorsPerTrack);
+ G16(p + 26, NumHeads);
+ G32(p + 28, NumHiddenSectors);
+ if (Get32(p + 32) != 0) // NumSectors32
+ return false;
+
+ // DriveNumber = p[0x24];
+ if (p[0x25] != 0) // CurrentHead
+ return false;
+ if (p[0x26] != 0x80) // ExtendedBootSig
+ return false;
+ if (p[0x27] != 0) // reserved
+ return false;
+ UInt64 numSectors = Get64(p + 0x28);
+ NumClusters = numSectors >> sectorsPerClusterLog;
+
+ G64(p + 0x30, MftCluster);
+ // G64(p + 0x38, Mft2Cluster);
+ G64(p + 0x48, SerialNumber);
+ UInt32 numClustersInMftRec;
+ UInt32 numClustersInIndexBlock;
+ G32(p + 0x40, numClustersInMftRec);
+ G32(p + 0x44, numClustersInIndexBlock);
+ return (numClustersInMftRec < 256 && numClustersInIndexBlock < 256);
+}
+
+struct CMftRef
+{
+ UInt64 Val;
+ UInt64 GetIndex() const { return Val & (((UInt64)1 << 48) - 1); }
+ UInt16 GetNumber() const { return (UInt16)(Val >> 48); }
+ bool IsBaseItself() const { return Val == 0; }
+};
+
+#define ATNAME(n) ATTR_TYPE_ ## n
+#define DEF_ATTR_TYPE(v, n) ATNAME(n) = v
+
+typedef enum
+{
+ DEF_ATTR_TYPE(0x00, UNUSED),
+ DEF_ATTR_TYPE(0x10, STANDARD_INFO),
+ DEF_ATTR_TYPE(0x20, ATTRIBUTE_LIST),
+ DEF_ATTR_TYPE(0x30, FILE_NAME),
+ DEF_ATTR_TYPE(0x40, OBJECT_ID),
+ DEF_ATTR_TYPE(0x50, SECURITY_DESCRIPTOR),
+ DEF_ATTR_TYPE(0x60, VOLUME_NAME),
+ DEF_ATTR_TYPE(0x70, VOLUME_INFO),
+ DEF_ATTR_TYPE(0x80, DATA),
+ DEF_ATTR_TYPE(0x90, INDEX_ROOT),
+ DEF_ATTR_TYPE(0xA0, INDEX_ALLOCATION),
+ DEF_ATTR_TYPE(0xB0, BITMAP),
+ DEF_ATTR_TYPE(0xC0, REPARSE_POINT),
+ DEF_ATTR_TYPE(0xD0, EA_INFO),
+ DEF_ATTR_TYPE(0xE0, EA),
+ DEF_ATTR_TYPE(0xF0, PROPERTY_SET),
+ DEF_ATTR_TYPE(0x100, LOGGED_UTILITY_STREAM),
+ DEF_ATTR_TYPE(0x1000, FIRST_USER_DEFINED_ATTRIBUTE)
+};
+
+static const Byte kFileNameType_Posix = 0;
+static const Byte kFileNameType_Win32 = 1;
+static const Byte kFileNameType_Dos = 2;
+static const Byte kFileNameType_Win32Dos = 3;
+
+struct CFileNameAttr
+{
+ CMftRef ParentDirRef;
+ // UInt64 CTime;
+ // UInt64 MTime;
+ // UInt64 ThisRecMTime;
+ // UInt64 ATime;
+ // UInt64 AllocatedSize;
+ // UInt64 DataSize;
+ // UInt16 PackedEaSize;
+ UString Name;
+ UInt32 Attrib;
+ Byte NameType;
+
+ bool IsDos() const { return NameType == kFileNameType_Dos; }
+ bool Parse(const Byte *p, unsigned size);
+};
+
+static void GetString(const Byte *p, unsigned length, UString &res)
+{
+ wchar_t *s = res.GetBuffer(length);
+ for (unsigned i = 0; i < length; i++)
+ s[i] = Get16(p + i * 2);
+ s[length] = 0;
+ res.ReleaseBuffer();
+}
+
+bool CFileNameAttr::Parse(const Byte *p, unsigned size)
+{
+ if (size < 0x42)
+ return false;
+ G64(p + 0x00, ParentDirRef.Val);
+ // G64(p + 0x08, CTime);
+ // G64(p + 0x10, MTime);
+ // G64(p + 0x18, ThisRecMTime);
+ // G64(p + 0x20, ATime);
+ // G64(p + 0x28, AllocatedSize);
+ // G64(p + 0x30, DataSize);
+ G32(p + 0x38, Attrib);
+ // G16(p + 0x3C, PackedEaSize);
+ NameType = p[0x41];
+ unsigned length = p[0x40];
+ if (0x42 + length > size)
+ return false;
+ GetString(p + 0x42, length, Name);
+ return true;
+}
+
+struct CSiAttr
+{
+ UInt64 CTime;
+ UInt64 MTime;
+ // UInt64 ThisRecMTime;
+ UInt64 ATime;
+ UInt32 Attrib;
+
+ /*
+ UInt32 MaxVersions;
+ UInt32 Version;
+ UInt32 ClassId;
+ UInt32 OwnerId;
+ UInt32 SecurityId;
+ UInt64 QuotaCharged;
+ */
+
+ bool Parse(const Byte *p, unsigned size);
+};
+
+bool CSiAttr::Parse(const Byte *p, unsigned size)
+{
+ if (size < 0x24)
+ return false;
+ G64(p + 0x00, CTime);
+ G64(p + 0x08, MTime);
+ // G64(p + 0x10, ThisRecMTime);
+ G64(p + 0x18, ATime);
+ G32(p + 0x20, Attrib);
+ return true;
+}
+
+static const UInt64 kEmptyExtent = (UInt64)(Int64)-1;
+
+struct CExtent
+{
+ UInt64 Virt;
+ UInt64 Phy;
+
+ bool IsEmpty() const { return Phy == kEmptyExtent; }
+};
+
+struct CVolInfo
+{
+ Byte MajorVer;
+ Byte MinorVer;
+ // UInt16 Flags;
+
+ bool Parse(const Byte *p, unsigned size);
+};
+
+bool CVolInfo::Parse(const Byte *p, unsigned size)
+{
+ if (size < 12)
+ return false;
+ MajorVer = p[8];
+ MinorVer = p[9];
+ // Flags = Get16(p + 10);
+ return true;
+}
+
+struct CAttr
+{
+ UInt32 Type;
+ // UInt32 Length;
+ UString Name;
+ // UInt16 Flags;
+ // UInt16 Instance;
+ CByteBuffer Data;
+ Byte NonResident;
+
+ // Non-Resident
+ Byte CompressionUnit;
+ UInt64 LowVcn;
+ UInt64 HighVcn;
+ UInt64 AllocatedSize;
+ UInt64 Size;
+ UInt64 PackSize;
+ UInt64 InitializedSize;
+
+ // Resident
+ // UInt16 ResidentFlags;
+
+ bool IsCompressionUnitSupported() const { return CompressionUnit == 0 || CompressionUnit == 4; }
+
+ UInt32 Parse(const Byte *p, unsigned size);
+ bool ParseFileName(CFileNameAttr &a) const { return a.Parse(Data, (unsigned)Data.GetCapacity()); }
+ bool ParseSi(CSiAttr &a) const { return a.Parse(Data, (unsigned)Data.GetCapacity()); }
+ bool ParseVolInfo(CVolInfo &a) const { return a.Parse(Data, (unsigned)Data.GetCapacity()); }
+ bool ParseExtents(CRecordVector<CExtent> &extents, UInt64 numClustersMax, int compressionUnit) const;
+ UInt64 GetSize() const { return NonResident ? Size : Data.GetCapacity(); }
+ UInt64 GetPackSize() const
+ {
+ if (!NonResident)
+ return Data.GetCapacity();
+ if (CompressionUnit != 0)
+ return PackSize;
+ return AllocatedSize;
+ }
+};
+
+#define RINOZ(x) { int __tt = (x); if (__tt != 0) return __tt; }
+
+static int CompareAttr(void *const *elem1, void *const *elem2, void *)
+{
+ const CAttr &a1 = *(*((const CAttr **)elem1));
+ const CAttr &a2 = *(*((const CAttr **)elem2));
+ RINOZ(MyCompare(a1.Type, a2.Type));
+ RINOZ(MyCompare(a1.Name, a2.Name));
+ return MyCompare(a1.LowVcn, a2.LowVcn);
+}
+
+UInt32 CAttr::Parse(const Byte *p, unsigned size)
+{
+ if (size < 4)
+ return 0;
+ G32(p, Type);
+ if (Type == 0xFFFFFFFF)
+ return 4;
+ if (size < 0x18)
+ return 0;
+ PRF(printf(" T=%2X", Type));
+
+ UInt32 length = Get32(p + 0x04);
+ PRF(printf(" L=%3d", length));
+ if (length > size)
+ return 0;
+ NonResident = p[0x08];
+ {
+ int nameLength = p[9];
+ UInt32 nameOffset = Get16(p + 0x0A);
+ if (nameLength != 0)
+ {
+ if (nameOffset + nameLength * 2 > length)
+ return 0;
+ GetString(p + nameOffset, nameLength, Name);
+ PRF(printf(" N=%S", Name));
+ }
+ }
+
+ // G16(p + 0x0C, Flags);
+ // G16(p + 0x0E, Instance);
+ // PRF(printf(" F=%4X", Flags));
+ // PRF(printf(" Inst=%d", Instance));
+
+ UInt32 dataSize;
+ UInt32 offs;
+ if (NonResident)
+ {
+ if (length < 0x40)
+ return 0;
+ PRF(printf(" NR"));
+ G64(p + 0x10, LowVcn);
+ G64(p + 0x18, HighVcn);
+ G64(p + 0x28, AllocatedSize);
+ G64(p + 0x30, Size);
+ G64(p + 0x38, InitializedSize);
+ G16(p + 0x20, offs);
+ CompressionUnit = p[0x22];
+
+ PackSize = Size;
+ if (CompressionUnit != 0)
+ {
+ if (length < 0x48)
+ return 0;
+ G64(p + 0x40, PackSize);
+ PRF(printf(" PS=%I64x", PackSize));
+ }
+
+ // PRF(printf("\n"));
+ PRF(printf(" ASize=%4I64d", AllocatedSize));
+ PRF(printf(" Size=%I64d", Size));
+ PRF(printf(" IS=%I64d", InitializedSize));
+ PRF(printf(" Low=%I64d", LowVcn));
+ PRF(printf(" High=%I64d", HighVcn));
+ PRF(printf(" CU=%d", (int)CompressionUnit));
+ dataSize = length - offs;
+ }
+ else
+ {
+ if (length < 0x18)
+ return 0;
+ PRF(printf(" RES"));
+ dataSize = Get32(p + 0x10);
+ PRF(printf(" dataSize=%3d", dataSize));
+ offs = Get16(p + 0x14);
+ // G16(p + 0x16, ResidentFlags);
+ // PRF(printf(" ResFlags=%4X", ResidentFlags));
+ }
+ if (offs > length || dataSize > length || length - dataSize < offs)
+ return 0;
+ Data.SetCapacity(dataSize);
+ memcpy(Data, p + offs, dataSize);
+ #ifdef SHOW_DEBUG_INFO
+ PRF(printf(" : "));
+ for (unsigned i = 0; i < Data.GetCapacity(); i++)
+ {
+ PRF(printf(" %02X", (int)Data[i]));
+ }
+ #endif
+ return length;
+}
+
+bool CAttr::ParseExtents(CRecordVector<CExtent> &extents, UInt64 numClustersMax, int compressionUnit) const
+{
+ const Byte *p = Data;
+ unsigned size = (unsigned)Data.GetCapacity();
+ UInt64 vcn = LowVcn;
+ UInt64 lcn = 0;
+ UInt64 highVcn1 = HighVcn + 1;
+ if (LowVcn != extents.Back().Virt || highVcn1 > (UInt64)1 << 63)
+ return false;
+
+ extents.DeleteBack();
+
+ PRF2(printf("\n# ParseExtents # LowVcn = %4I64X # HighVcn = %4I64X", LowVcn, HighVcn));
+
+ while (size > 0)
+ {
+ Byte b = *p++;
+ size--;
+ if (b == 0)
+ break;
+ UInt32 num = b & 0xF;
+ if (num == 0 || num > 8 || num > size)
+ return false;
+
+ int i;
+ UInt64 vSize = p[num - 1];
+ for (i = (int)num - 2; i >= 0; i--)
+ vSize = (vSize << 8) | p[i];
+ if (vSize == 0)
+ return false;
+ p += num;
+ size -= num;
+ if ((highVcn1 - vcn) < vSize)
+ return false;
+
+ num = (b >> 4) & 0xF;
+ if (num > 8 || num > size)
+ return false;
+ CExtent e;
+ e.Virt = vcn;
+ if (num == 0)
+ {
+ if (compressionUnit == 0)
+ return false;
+ e.Phy = kEmptyExtent;
+ }
+ else
+ {
+ Int64 v = (signed char)p[num - 1];
+ for (i = (int)num - 2; i >= 0; i--)
+ v = (v << 8) | p[i];
+ p += num;
+ size -= num;
+ lcn += v;
+ if (lcn > numClustersMax)
+ return false;
+ e.Phy = lcn;
+ }
+ extents.Add(e);
+ vcn += vSize;
+ }
+ CExtent e;
+ e.Phy = kEmptyExtent;
+ e.Virt = vcn;
+ extents.Add(e);
+ return (highVcn1 == vcn);
+}
+
+static const UInt64 kEmptyTag = (UInt64)(Int64)-1;
+
+static const int kNumCacheChunksLog = 1;
+static const UInt32 kNumCacheChunks = (1 << kNumCacheChunksLog);
+
+class CInStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+ UInt64 _virtPos;
+ UInt64 _physPos;
+ UInt64 _curRem;
+ bool _sparseMode;
+ size_t _compressedPos;
+
+ UInt64 _tags[kNumCacheChunks];
+ int _chunkSizeLog;
+ CByteBuffer _inBuf;
+ CByteBuffer _outBuf;
+public:
+ CMyComPtr<IInStream> Stream;
+ UInt64 Size;
+ UInt64 InitializedSize;
+ int BlockSizeLog;
+ int CompressionUnit;
+ bool InUse;
+ CRecordVector<CExtent> Extents;
+
+ HRESULT SeekToPhys() { return Stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
+
+ UInt32 GetCuSize() const { return (UInt32)1 << (BlockSizeLog + CompressionUnit); }
+ HRESULT InitAndSeek(int compressionUnit)
+ {
+ CompressionUnit = compressionUnit;
+ if (compressionUnit != 0)
+ {
+ UInt32 cuSize = GetCuSize();
+ _inBuf.SetCapacity(cuSize);
+ _chunkSizeLog = BlockSizeLog + CompressionUnit;
+ _outBuf.SetCapacity(kNumCacheChunks << _chunkSizeLog);
+ }
+ for (int i = 0; i < kNumCacheChunks; i++)
+ _tags[i] = kEmptyTag;
+
+ _sparseMode = false;
+ _curRem = 0;
+ _virtPos = 0;
+ _physPos = 0;
+ const CExtent &e = Extents[0];
+ if (!e.IsEmpty())
+ _physPos = e.Phy << BlockSizeLog;
+ return SeekToPhys();
+ }
+
+ MY_UNKNOWN_IMP1(IInStream)
+
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+static size_t Lznt1Dec(Byte *dest, size_t outBufLim, size_t destLen, const Byte *src, size_t srcLen)
+{
+ size_t destSize = 0;
+ while (destSize < destLen)
+ {
+ if (srcLen < 2 || (destSize & 0xFFF) != 0)
+ break;
+ UInt32 v = Get16(src);
+ if (v == 0)
+ break;
+ src += 2;
+ srcLen -= 2;
+ UInt32 comprSize = (v & 0xFFF) + 1;
+ if (comprSize > srcLen)
+ break;
+ srcLen -= comprSize;
+ if ((v & 0x8000) == 0)
+ {
+ if (comprSize != (1 << 12))
+ break;
+ memcpy(dest + destSize, src, comprSize);
+ src += comprSize;
+ destSize += comprSize;
+ }
+ else
+ {
+ if (destSize + (1 << 12) > outBufLim || (src[0] & 1) != 0)
+ return 0;
+ int numDistBits = 4;
+ UInt32 sbOffset = 0;
+ UInt32 pos = 0;
+
+ do
+ {
+ comprSize--;
+ for (UInt32 mask = src[pos++] | 0x100; mask > 1 && comprSize > 0; mask >>= 1)
+ {
+ if ((mask & 1) == 0)
+ {
+ if (sbOffset >= (1 << 12))
+ return 0;
+ dest[destSize++] = src[pos++];
+ sbOffset++;
+ comprSize--;
+ }
+ else
+ {
+ if (comprSize < 2)
+ return 0;
+ UInt32 v = Get16(src + pos);
+ pos += 2;
+ comprSize -= 2;
+
+ while (((sbOffset - 1) >> numDistBits) != 0)
+ numDistBits++;
+
+ UInt32 len = (v & (0xFFFF >> numDistBits)) + 3;
+ if (sbOffset + len > (1 << 12))
+ return 0;
+ UInt32 dist = (v >> (16 - numDistBits));
+ if (dist >= sbOffset)
+ return 0;
+ Int32 offs = -1 - dist;
+ Byte *p = dest + destSize;
+ for (UInt32 t = 0; t < len; t++)
+ p[t] = p[t + offs];
+ destSize += len;
+ sbOffset += len;
+ }
+ }
+ }
+ while (comprSize > 0);
+ src += pos;
+ }
+ }
+ return destSize;
+}
+
+STDMETHODIMP CInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_virtPos >= Size)
+ return (Size == _virtPos) ? S_OK: E_FAIL;
+ if (size == 0)
+ return S_OK;
+ UInt64 rem = Size - _virtPos;
+ if (size > rem)
+ size = (UInt32)rem;
+ if (_virtPos >= InitializedSize)
+ {
+ memset((Byte *)data, 0, size);
+ _virtPos += size;
+ *processedSize = size;
+ return S_OK;
+ }
+ rem = InitializedSize - _virtPos;
+ if (size > rem)
+ size = (UInt32)rem;
+
+ while (_curRem == 0)
+ {
+ UInt64 cacheTag = _virtPos >> _chunkSizeLog;
+ UInt32 cacheIndex = (UInt32)cacheTag & (kNumCacheChunks - 1);
+ if (_tags[cacheIndex] == cacheTag)
+ {
+ UInt32 chunkSize = (UInt32)1 << _chunkSizeLog;
+ UInt32 offset = (UInt32)_virtPos & (chunkSize - 1);
+ UInt32 cur = MyMin(chunkSize - offset, size);
+ memcpy(data, _outBuf + (cacheIndex << _chunkSizeLog) + offset, cur);
+ *processedSize = cur;
+ _virtPos += cur;
+ return S_OK;
+ }
+
+ PRF2(printf("\nVirtPos = %6d", _virtPos));
+
+ UInt32 comprUnitSize = (UInt32)1 << CompressionUnit;
+ UInt64 virtBlock = _virtPos >> BlockSizeLog;
+ UInt64 virtBlock2 = virtBlock & ~((UInt64)comprUnitSize - 1);
+
+ int left = 0, right = Extents.Size();
+ for (;;)
+ {
+ int mid = (left + right) / 2;
+ if (mid == left)
+ break;
+ if (virtBlock2 < Extents[mid].Virt)
+ right = mid;
+ else
+ left = mid;
+ }
+
+ bool isCompressed = false;
+ UInt64 virtBlock2End = virtBlock2 + comprUnitSize;
+ if (CompressionUnit != 0)
+ for (int i = left; i < Extents.Size(); i++)
+ {
+ const CExtent &e = Extents[i];
+ if (e.Virt >= virtBlock2End)
+ break;
+ if (e.IsEmpty())
+ {
+ isCompressed = true;
+ break;
+ }
+ }
+
+ int i;
+ for (i = left; Extents[i + 1].Virt <= virtBlock; i++);
+
+ _sparseMode = false;
+ if (!isCompressed)
+ {
+ const CExtent &e = Extents[i];
+ UInt64 newPos = (e.Phy << BlockSizeLog) + _virtPos - (e.Virt << BlockSizeLog);
+ if (newPos != _physPos)
+ {
+ _physPos = newPos;
+ RINOK(SeekToPhys());
+ }
+ UInt64 next = Extents[i + 1].Virt;
+ if (next > virtBlock2End)
+ next &= ~((UInt64)comprUnitSize - 1);
+ next <<= BlockSizeLog;
+ if (next > Size)
+ next = Size;
+ _curRem = next - _virtPos;
+ break;
+ }
+ bool thereArePhy = false;
+ for (int i2 = left; i2 < Extents.Size(); i2++)
+ {
+ const CExtent &e = Extents[i2];
+ if (e.Virt >= virtBlock2End)
+ break;
+ if (!e.IsEmpty())
+ {
+ thereArePhy = true;
+ break;
+ }
+ }
+ if (!thereArePhy)
+ {
+ _curRem = (Extents[i + 1].Virt << BlockSizeLog) - _virtPos;
+ _sparseMode = true;
+ break;
+ }
+
+ size_t offs = 0;
+ UInt64 curVirt = virtBlock2;
+ for (i = left; i < Extents.Size(); i++)
+ {
+ const CExtent &e = Extents[i];
+ if (e.IsEmpty())
+ break;
+ if (e.Virt >= virtBlock2End)
+ return S_FALSE;
+ UInt64 newPos = (e.Phy + (curVirt - e.Virt)) << BlockSizeLog;
+ if (newPos != _physPos)
+ {
+ _physPos = newPos;
+ RINOK(SeekToPhys());
+ }
+ UInt64 numChunks = Extents[i + 1].Virt - curVirt;
+ if (curVirt + numChunks > virtBlock2End)
+ numChunks = virtBlock2End - curVirt;
+ size_t compressed = (size_t)numChunks << BlockSizeLog;
+ RINOK(ReadStream_FALSE(Stream, _inBuf + offs, compressed));
+ curVirt += numChunks;
+ _physPos += compressed;
+ offs += compressed;
+ }
+ size_t destLenMax = GetCuSize();
+ size_t destLen = destLenMax;
+ UInt64 rem = Size - (virtBlock2 << BlockSizeLog);
+ if (destLen > rem)
+ destLen = (size_t)rem;
+
+ Byte *dest = _outBuf + (cacheIndex << _chunkSizeLog);
+ size_t destSizeRes = Lznt1Dec(dest, destLenMax, destLen, _inBuf, offs);
+ _tags[cacheIndex] = cacheTag;
+
+ // some files in Vista have destSize > destLen
+ if (destSizeRes < destLen)
+ {
+ memset(dest, 0, destLenMax);
+ if (InUse)
+ return S_FALSE;
+ }
+ }
+ if (size > _curRem)
+ size = (UInt32)_curRem;
+ HRESULT res = S_OK;
+ if (_sparseMode)
+ memset(data, 0, size);
+ else
+ {
+ res = Stream->Read(data, size, &size);
+ _physPos += size;
+ }
+ if (processedSize != NULL)
+ *processedSize = size;
+ _virtPos += size;
+ _curRem -= size;
+ return res;
+}
+
+STDMETHODIMP CInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ UInt64 newVirtPos = offset;
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: break;
+ case STREAM_SEEK_CUR: newVirtPos += _virtPos; break;
+ case STREAM_SEEK_END: newVirtPos += Size; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (_virtPos != newVirtPos)
+ _curRem = 0;
+ _virtPos = newVirtPos;
+ if (newPosition)
+ *newPosition = newVirtPos;
+ return S_OK;
+}
+
+class CByteBufStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+ UInt64 _virtPos;
+public:
+ CByteBuffer Buf;
+ void Init() { _virtPos = 0; }
+
+ MY_UNKNOWN_IMP1(IInStream)
+
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+STDMETHODIMP CByteBufStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_virtPos >= Buf.GetCapacity())
+ return (_virtPos == Buf.GetCapacity()) ? S_OK: E_FAIL;
+ UInt64 rem = Buf.GetCapacity() - _virtPos;
+ if (rem < size)
+ size = (UInt32)rem;
+ memcpy(data, Buf + (size_t)_virtPos, size);
+ if (processedSize != NULL)
+ *processedSize = size;
+ _virtPos += size;
+ return S_OK;
+}
+
+STDMETHODIMP CByteBufStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: _virtPos = offset; break;
+ case STREAM_SEEK_CUR: _virtPos += offset; break;
+ case STREAM_SEEK_END: _virtPos = Buf.GetCapacity() + offset; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (newPosition)
+ *newPosition = _virtPos;
+ return S_OK;
+}
+
+HRESULT DataParseExtents(int clusterSizeLog, const CObjectVector<CAttr> attrs,
+ int attrIndex, int attrIndexLim, UInt64 numPhysClusters, CRecordVector<CExtent> &Extents)
+{
+ CExtent e;
+ e.Virt = 0;
+ e.Phy = kEmptyExtent;
+ Extents.Add(e);
+ const CAttr &attr0 = attrs[attrIndex];
+
+ if (attr0.AllocatedSize < attr0.Size ||
+ (attrs[attrIndexLim - 1].HighVcn + 1) != (attr0.AllocatedSize >> clusterSizeLog) ||
+ (attr0.AllocatedSize & ((1 << clusterSizeLog) - 1)) != 0)
+ return S_FALSE;
+
+ for (int i = attrIndex; i < attrIndexLim; i++)
+ if (!attrs[i].ParseExtents(Extents, numPhysClusters, attr0.CompressionUnit))
+ return S_FALSE;
+
+ UInt64 packSizeCalc = 0;
+ for (int k = 0; k < Extents.Size(); k++)
+ {
+ CExtent &e = Extents[k];
+ if (!e.IsEmpty())
+ packSizeCalc += (Extents[k + 1].Virt - e.Virt) << clusterSizeLog;
+ PRF2(printf("\nSize = %4I64X", Extents[k + 1].Virt - e.Virt));
+ PRF2(printf(" Pos = %4I64X", e.Phy));
+ }
+
+ if (attr0.CompressionUnit != 0)
+ {
+ if (packSizeCalc != attr0.PackSize)
+ return S_FALSE;
+ }
+ else
+ {
+ if (packSizeCalc != attr0.AllocatedSize)
+ return S_FALSE;
+ }
+ return S_OK;
+}
+
+struct CDataRef
+{
+ int Start;
+ int Num;
+};
+
+struct CMftRec
+{
+ UInt32 Magic;
+ // UInt64 Lsn;
+ UInt16 SeqNumber;
+ UInt16 Flags;
+ // UInt16 LinkCount;
+ // UInt16 NextAttrInstance;
+ CMftRef BaseMftRef;
+ // UInt32 ThisRecNumber;
+ UInt32 MyNumNameLinks;
+
+ CObjectVector<CAttr> DataAttrs;
+ CObjectVector<CFileNameAttr> FileNames;
+ CRecordVector<CDataRef> DataRefs;
+
+ CSiAttr SiAttr;
+
+
+ void MoveAttrsFrom(CMftRec &src)
+ {
+ DataAttrs += src.DataAttrs;
+ FileNames += src.FileNames;
+ src.DataAttrs.ClearAndFree();
+ src.FileNames.ClearAndFree();
+ }
+
+ UInt64 GetPackSize() const
+ {
+ UInt64 res = 0;
+ for (int i = 0; i < DataRefs.Size(); i++)
+ res += DataAttrs[DataRefs[i].Start].GetPackSize();
+ return res;
+ }
+
+ bool Parse(Byte *p, int sectorSizeLog, UInt32 numSectors, UInt32 recNumber, CObjectVector<CAttr> *attrs);
+
+ bool IsEmpty() const { return (Magic <= 2); }
+
+ bool InUse() const { return (Flags & 1) != 0; }
+ bool IsDir() const { return (Flags & 2) != 0; }
+
+ void ParseDataNames();
+ HRESULT GetStream(IInStream *mainStream, int dataIndex,
+ int clusterSizeLog, UInt64 numPhysClusters, IInStream **stream) const;
+
+ UInt64 GetSize(int dataIndex) const { return DataAttrs[DataRefs[dataIndex].Start].GetSize(); }
+
+ CMftRec(): MyNumNameLinks(0) {}
+};
+
+void CMftRec::ParseDataNames()
+{
+ DataRefs.Clear();
+ DataAttrs.Sort(CompareAttr, 0);
+
+ for (int i = 0; i < DataAttrs.Size();)
+ {
+ CDataRef ref;
+ ref.Start = i;
+ for (i++; i < DataAttrs.Size(); i++)
+ if (DataAttrs[ref.Start].Name != DataAttrs[i].Name)
+ break;
+ ref.Num = i - ref.Start;
+ DataRefs.Add(ref);
+ }
+}
+
+HRESULT CMftRec::GetStream(IInStream *mainStream, int dataIndex,
+ int clusterSizeLog, UInt64 numPhysClusters, IInStream **destStream) const
+{
+ *destStream = 0;
+ CByteBufStream *streamSpec = new CByteBufStream;
+ CMyComPtr<IInStream> streamTemp = streamSpec;
+
+ if (dataIndex < 0)
+ return E_FAIL;
+
+ if (dataIndex < DataRefs.Size())
+ {
+ const CDataRef &ref = DataRefs[dataIndex];
+ int numNonResident = 0;
+ int i;
+ for (i = ref.Start; i < ref.Start + ref.Num; i++)
+ if (DataAttrs[i].NonResident)
+ numNonResident++;
+
+ const CAttr &attr0 = DataAttrs[ref.Start];
+
+ if (numNonResident != 0 || ref.Num != 1)
+ {
+ if (numNonResident != ref.Num || !attr0.IsCompressionUnitSupported())
+ return S_FALSE;
+ CInStream *streamSpec = new CInStream;
+ CMyComPtr<IInStream> streamTemp = streamSpec;
+ RINOK(DataParseExtents(clusterSizeLog, DataAttrs, ref.Start, ref.Start + ref.Num, numPhysClusters, streamSpec->Extents));
+ streamSpec->Size = attr0.Size;
+ streamSpec->InitializedSize = attr0.InitializedSize;
+ streamSpec->Stream = mainStream;
+ streamSpec->BlockSizeLog = clusterSizeLog;
+ streamSpec->InUse = InUse();
+ RINOK(streamSpec->InitAndSeek(attr0.CompressionUnit));
+ *destStream = streamTemp.Detach();
+ return S_OK;
+ }
+ streamSpec->Buf = attr0.Data;
+ }
+ streamSpec->Init();
+ *destStream = streamTemp.Detach();
+ return S_OK;
+}
+
+bool CMftRec::Parse(Byte *p, int sectorSizeLog, UInt32 numSectors, UInt32 recNumber,
+ CObjectVector<CAttr> *attrs)
+{
+ G32(p, Magic);
+ if (IsEmpty())
+ return true;
+ if (Magic != 0x454c4946)
+ return false;
+
+ UInt32 usaOffset;
+ UInt32 numUsaItems;
+ G16(p + 0x04, usaOffset);
+ G16(p + 0x06, numUsaItems);
+
+ if ((usaOffset & 1) != 0 || usaOffset + numUsaItems * 2 > ((UInt32)1 << sectorSizeLog) - 2 ||
+ numUsaItems == 0 || numUsaItems - 1 != numSectors)
+ return false;
+
+ UInt16 usn = Get16(p + usaOffset);
+ // PRF(printf("\nusn = %d", usn));
+ for (UInt32 i = 1; i < numUsaItems; i++)
+ {
+ void *pp = p + (i << sectorSizeLog) - 2;
+ if (Get16(pp) != usn)
+ return false;
+ SetUi16(pp, Get16(p + usaOffset + i * 2));
+ }
+
+ // G64(p + 0x08, Lsn);
+ G16(p + 0x10, SeqNumber);
+ // G16(p + 0x12, LinkCount);
+ // PRF(printf(" L=%d", LinkCount));
+ UInt32 attrOffs = Get16(p + 0x14);
+ G16(p + 0x16, Flags);
+ PRF(printf(" F=%4X", Flags));
+
+ UInt32 bytesInUse = Get32(p + 0x18);
+ UInt32 bytesAlloc = Get32(p + 0x1C);
+ G64(p + 0x20, BaseMftRef.Val);
+ if (BaseMftRef.Val != 0)
+ {
+ PRF(printf(" BaseRef=%d", (int)BaseMftRef.Val));
+ // return false; // Check it;
+ }
+ // G16(p + 0x28, NextAttrInstance);
+ if (usaOffset >= 0x30)
+ if (Get32(p + 0x2C) != recNumber) // NTFS 3.1+
+ return false;
+
+ UInt32 limit = numSectors << sectorSizeLog;
+ if (attrOffs >= limit || (attrOffs & 7) != 0 || bytesInUse > limit
+ || bytesAlloc != limit)
+ return false;
+
+
+ for (UInt32 t = attrOffs; t < limit;)
+ {
+ CAttr attr;
+ // PRF(printf("\n %2d:", Attrs.Size()));
+ PRF(printf("\n"));
+ UInt32 length = attr.Parse(p + t, limit - t);
+ if (length == 0 || limit - t < length)
+ return false;
+ t += length;
+ if (attr.Type == 0xFFFFFFFF)
+ break;
+ switch(attr.Type)
+ {
+ case ATTR_TYPE_FILE_NAME:
+ {
+ CFileNameAttr fna;
+ if (!attr.ParseFileName(fna))
+ return false;
+ FileNames.Add(fna);
+ PRF(printf(" flags = %4x", (int)fna.NameType));
+ PRF(printf("\n %S", fna.Name));
+ break;
+ }
+ case ATTR_TYPE_STANDARD_INFO:
+ if (!attr.ParseSi(SiAttr))
+ return false;
+ break;
+ case ATTR_TYPE_DATA:
+ DataAttrs.Add(attr);
+ break;
+ default:
+ if (attrs)
+ attrs->Add(attr);
+ break;
+ }
+ }
+
+ return true;
+}
+
+struct CItem
+{
+ int RecIndex;
+ int DataIndex;
+ CMftRef ParentRef;
+ UString Name;
+ UInt32 Attrib;
+
+ bool IsDir() const { return (DataIndex < 0); }
+};
+
+struct CDatabase
+{
+ CHeader Header;
+ CObjectVector<CItem> Items;
+ CObjectVector<CMftRec> Recs;
+ CMyComPtr<IInStream> InStream;
+ IArchiveOpenCallback *OpenCallback;
+
+ CByteBuffer ByteBuf;
+
+ CObjectVector<CAttr> VolAttrs;
+
+ ~CDatabase() { ClearAndClose(); }
+
+ void Clear();
+ void ClearAndClose();
+
+ UString GetItemPath(Int32 index) const;
+ HRESULT Open();
+ HRESULT ReadDir(Int32 parent, UInt32 cluster, int level);
+
+ HRESULT SeekToCluster(UInt64 cluster);
+
+ int FindMtfRec(const CMftRef &ref) const
+ {
+ UInt64 val = ref.GetIndex();
+ int left = 0, right = Items.Size();
+ while (left != right)
+ {
+ int mid = (left + right) / 2;
+ UInt64 midValue = Items[mid].RecIndex;
+ if (val == midValue)
+ return mid;
+ if (val < midValue)
+ right = mid;
+ else
+ left = mid + 1;
+ }
+ return -1;
+ }
+
+};
+
+HRESULT CDatabase::SeekToCluster(UInt64 cluster)
+{
+ return InStream->Seek(cluster << Header.ClusterSizeLog, STREAM_SEEK_SET, NULL);
+}
+
+void CDatabase::Clear()
+{
+ Items.Clear();
+ Recs.Clear();
+}
+
+void CDatabase::ClearAndClose()
+{
+ Clear();
+ InStream.Release();
+}
+
+#define MY_DIR_PREFIX(x) L"[" x L"]" WSTRING_PATH_SEPARATOR
+
+UString CDatabase::GetItemPath(Int32 index) const
+{
+ const CItem *item = &Items[index];
+ UString name = item->Name;
+ for (int j = 0; j < 256; j++)
+ {
+ CMftRef ref = item->ParentRef;
+ index = FindMtfRec(ref);
+ if (ref.GetIndex() == 5)
+ return name;
+ if (index < 0 || Recs[Items[index].RecIndex].SeqNumber != ref.GetNumber())
+ return MY_DIR_PREFIX(L"UNKNOWN") + name;
+ item = &Items[index];
+ name = item->Name + WCHAR_PATH_SEPARATOR + name;
+ }
+ return MY_DIR_PREFIX(L"BAD") + name;
+}
+
+HRESULT CDatabase::Open()
+{
+ Clear();
+
+ static const UInt32 kHeaderSize = 512;
+ Byte buf[kHeaderSize];
+ RINOK(ReadStream_FALSE(InStream, buf, kHeaderSize));
+ if (!Header.Parse(buf))
+ return S_FALSE;
+ UInt64 fileSize;
+ RINOK(InStream->Seek(0, STREAM_SEEK_END, &fileSize));
+ if (fileSize < Header.GetPhySize())
+ return S_FALSE;
+
+ SeekToCluster(Header.MftCluster);
+
+ CMftRec mftRec;
+ UInt32 numSectorsInRec;
+ int recSizeLog;
+ CMyComPtr<IInStream> mftStream;
+ {
+ UInt32 blockSize = 1 << 12;
+ ByteBuf.SetCapacity(blockSize);
+ RINOK(ReadStream_FALSE(InStream, ByteBuf, blockSize));
+
+ UInt32 allocSize = Get32(ByteBuf + 0x1C);
+ recSizeLog = GetLog(allocSize);
+ if (recSizeLog < Header.SectorSizeLog)
+ return false;
+ numSectorsInRec = 1 << (recSizeLog - Header.SectorSizeLog);
+ if (!mftRec.Parse(ByteBuf, Header.SectorSizeLog, numSectorsInRec, NULL, 0))
+ return S_FALSE;
+ if (mftRec.IsEmpty())
+ return S_FALSE;
+ mftRec.ParseDataNames();
+ if (mftRec.DataRefs.IsEmpty())
+ return S_FALSE;
+ RINOK(mftRec.GetStream(InStream, 0, Header.ClusterSizeLog, Header.NumClusters, &mftStream));
+ if (!mftStream)
+ return S_FALSE;
+ }
+
+ UInt64 mftSize = mftRec.DataAttrs[0].Size;
+ if ((mftSize >> 4) > Header.GetPhySize())
+ return S_FALSE;
+
+ UInt64 numFiles = mftSize >> recSizeLog;
+ if (numFiles > (1 << 30))
+ return S_FALSE;
+ if (OpenCallback)
+ {
+ RINOK(OpenCallback->SetTotal(&numFiles, &mftSize));
+ }
+ const UInt32 kBufSize = (1 << 15);
+ if (kBufSize < (1 << recSizeLog))
+ return S_FALSE;
+
+ ByteBuf.SetCapacity((size_t)kBufSize);
+ Recs.Reserve((int)numFiles);
+ for (UInt64 pos64 = 0;;)
+ {
+ if (OpenCallback)
+ {
+ // Sleep(0);
+ UInt64 numFiles = Recs.Size();
+ RINOK(OpenCallback->SetCompleted(&numFiles, &pos64));
+ }
+ UInt32 readSize = kBufSize;
+ UInt64 rem = mftSize - pos64;
+ if (readSize > rem)
+ readSize = (UInt32)rem;
+ if (readSize < ((UInt32)1 << recSizeLog))
+ break;
+ RINOK(ReadStream_FALSE(mftStream, ByteBuf, (size_t)readSize));
+ pos64 += readSize;
+ for (int i = 0; ((UInt32)(i + 1) << recSizeLog) <= readSize; i++)
+ {
+ PRF(printf("\n---------------------"));
+ PRF(printf("\n%5d:", Recs.Size()));
+ Byte *p = ByteBuf + ((UInt32)i << recSizeLog);
+ CMftRec rec;
+ if (!rec.Parse(p, Header.SectorSizeLog, numSectorsInRec, (UInt32)Recs.Size(),
+ (Recs.Size() == kRecIndex_Volume) ? &VolAttrs: NULL))
+ return S_FALSE;
+ Recs.Add(rec);
+ }
+ }
+
+ int i;
+ for (i = 0; i < Recs.Size(); i++)
+ {
+ CMftRec &rec = Recs[i];
+ if (!rec.BaseMftRef.IsBaseItself())
+ {
+ UInt64 refIndex = rec.BaseMftRef.GetIndex();
+ if (refIndex > (UInt32)Recs.Size())
+ return S_FALSE;
+ CMftRec &refRec = Recs[(int)refIndex];
+ bool moveAttrs = (refRec.SeqNumber == rec.BaseMftRef.GetNumber() && refRec.BaseMftRef.IsBaseItself());
+ if (rec.InUse() && refRec.InUse())
+ {
+ if (!moveAttrs)
+ return S_FALSE;
+ }
+ else if (rec.InUse() || refRec.InUse())
+ moveAttrs = false;
+ if (moveAttrs)
+ refRec.MoveAttrsFrom(rec);
+ }
+ }
+
+ for (i = 0; i < Recs.Size(); i++)
+ Recs[i].ParseDataNames();
+
+ for (i = 0; i < Recs.Size(); i++)
+ {
+ CMftRec &rec = Recs[i];
+ if (rec.IsEmpty() || !rec.BaseMftRef.IsBaseItself())
+ continue;
+ int numNames = 0;
+ // printf("\n%4d: ", i);
+ for (int t = 0; t < rec.FileNames.Size(); t++)
+ {
+ const CFileNameAttr &fna = rec.FileNames[t];
+ // printf("%4d %S | ", (int)fna.NameType, fna.Name);
+ if (fna.IsDos())
+ continue;
+ int numDatas = rec.DataRefs.Size();
+
+ // For hard linked files we show substreams only for first Name.
+ if (numDatas > 1 && numNames > 0)
+ numDatas = 1;
+ numNames++;
+
+ if (rec.IsDir())
+ {
+ CItem item;
+ item.Name = fna.Name;
+ item.RecIndex = i;
+ item.DataIndex = -1;
+ item.ParentRef = fna.ParentDirRef;
+ item.Attrib = rec.SiAttr.Attrib | 0x10;
+ // item.Attrib = fna.Attrib;
+ Items.Add(item);
+ }
+ for (int di = 0; di < numDatas; di++)
+ {
+ CItem item;
+ item.Name = fna.Name;
+ item.Attrib = rec.SiAttr.Attrib;
+ const UString &subName = rec.DataAttrs[rec.DataRefs[di].Start].Name;
+ if (!subName.IsEmpty())
+ {
+ // $BadClus:$Bad is sparse file for all clusters. So we skip it.
+ if (i == kRecIndex_BadClus && subName == L"$Bad")
+ continue;
+ item.Name += L":";
+ item.Name += subName;
+ item.Attrib = fna.Attrib;
+ }
+
+ PRF(printf("\n%3d", i));
+ PRF(printf(" attrib=%2x", rec.SiAttr.Attrib));
+ PRF(printf(" %S", item.Name));
+
+ item.RecIndex = i;
+ item.DataIndex = di;
+ item.ParentRef = fna.ParentDirRef;
+
+ Items.Add(item);
+ rec.MyNumNameLinks++;
+ }
+ }
+ rec.FileNames.ClearAndFree();
+ }
+
+ return S_OK;
+}
+
+class CHandler:
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp,
+ CDatabase
+{
+public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+};
+
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ IInStream *stream2;
+ const CItem &item = Items[index];
+ const CMftRec &rec = Recs[item.RecIndex];
+ HRESULT res = rec.GetStream(InStream, item.DataIndex, Header.ClusterSizeLog, Header.NumClusters, &stream2);
+ *stream = (ISequentialInStream *)stream2;
+ return res;
+ COM_TRY_END
+}
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidPath, VT_BSTR},
+ { NULL, kpidIsDir, VT_BOOL},
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidCTime, VT_FILETIME},
+ { NULL, kpidATime, VT_FILETIME},
+ { NULL, kpidAttrib, VT_UI4},
+ { NULL, kpidLinks, VT_UI4}
+};
+
+STATPROPSTG kArcProps[] =
+{
+ { NULL, kpidVolumeName, VT_BSTR},
+ { NULL, kpidFileSystem, VT_BSTR},
+ { NULL, kpidClusterSize, VT_UI4},
+ { NULL, kpidPhySize, VT_UI8},
+ { NULL, kpidHeadersSize, VT_UI8},
+ { NULL, kpidCTime, VT_FILETIME},
+
+ { NULL, kpidSectorSize, VT_UI4},
+ { NULL, kpidId, VT_UI8}
+ // { NULL, kpidSectorsPerTrack, VT_UI4},
+ // { NULL, kpidNumHeads, VT_UI4},
+ // { NULL, kpidHiddenSectors, VT_UI4}
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps
+
+static void NtfsTimeToProp(UInt64 t, NWindows::NCOM::CPropVariant &prop)
+{
+ FILETIME ft;
+ ft.dwLowDateTime = (DWORD)t;
+ ft.dwHighDateTime = (DWORD)(t >> 32);
+ prop = ft;
+}
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+
+ const CMftRec *volRec = (Recs.Size() > kRecIndex_Volume ? &Recs[kRecIndex_Volume] : NULL);
+
+ switch(propID)
+ {
+ case kpidClusterSize: prop = Header.ClusterSize(); break;
+ case kpidPhySize: prop = Header.GetPhySize(); break;
+ /*
+ case kpidHeadersSize:
+ {
+ UInt64 val = 0;
+ for (int i = 0; i < kNumSysRecs; i++)
+ {
+ printf("\n%2d: %8I64d ", i, Recs[i].GetPackSize());
+ if (i == 8)
+ i = i
+ val += Recs[i].GetPackSize();
+ }
+ prop = val;
+ break;
+ }
+ */
+ case kpidCTime: if (volRec) NtfsTimeToProp(volRec->SiAttr.CTime, prop); break;break;
+ case kpidVolumeName:
+ {
+ for (int i = 0; i < VolAttrs.Size(); i++)
+ {
+ const CAttr &attr = VolAttrs[i];
+ if (attr.Type == ATTR_TYPE_VOLUME_NAME)
+ {
+ UString name;
+ GetString(attr.Data, (int)attr.Data.GetCapacity() / 2, name);
+ prop = name;
+ break;
+ }
+ }
+ break;
+ }
+ case kpidFileSystem:
+ {
+ AString s = "NTFS";
+ for (int i = 0; i < VolAttrs.Size(); i++)
+ {
+ const CAttr &attr = VolAttrs[i];
+ if (attr.Type == ATTR_TYPE_VOLUME_INFO)
+ {
+ CVolInfo vi;
+ if (attr.ParseVolInfo(vi))
+ {
+ s += ' ';
+ char temp[16];
+ ConvertUInt32ToString(vi.MajorVer, temp);
+ s += temp;
+ s += '.';
+ ConvertUInt32ToString(vi.MinorVer, temp);
+ s += temp;
+ }
+ break;
+ }
+ }
+ prop = s;
+ break;
+ }
+ case kpidSectorSize: prop = (UInt32)1 << Header.SectorSizeLog; break;
+ case kpidId: prop = Header.SerialNumber; break;
+ // case kpidMediaType: prop = Header.MediaType; break;
+ // case kpidSectorsPerTrack: prop = Header.SectorsPerTrack; break;
+ // case kpidNumHeads: prop = Header.NumHeads; break;
+ // case kpidHiddenSectors: prop = Header.NumHiddenSectors; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ const CItem &item = Items[index];
+ const CMftRec &rec = Recs[item.RecIndex];
+
+ const CAttr *data= NULL;
+ if (item.DataIndex >= 0)
+ data = &rec.DataAttrs[rec.DataRefs[item.DataIndex].Start];
+
+ switch(propID)
+ {
+ case kpidPath:
+ {
+ UString name = GetItemPath(index);
+ const wchar_t *prefix = NULL;
+ if (!rec.InUse())
+ prefix = MY_DIR_PREFIX(L"DELETED");
+ else if (item.RecIndex < kNumSysRecs)
+ prefix = MY_DIR_PREFIX(L"SYSTEM");
+ if (prefix)
+ name = prefix + name;
+ prop = name;
+ break;
+ }
+
+ case kpidIsDir: prop = item.IsDir(); break;
+ case kpidMTime: NtfsTimeToProp(rec.SiAttr.MTime, prop); break;
+
+ case kpidCTime: NtfsTimeToProp(rec.SiAttr.CTime, prop); break;
+ case kpidATime: NtfsTimeToProp(rec.SiAttr.ATime, prop); break;
+ case kpidAttrib:
+ prop = item.Attrib;
+ break;
+ case kpidLinks: prop = rec.MyNumNameLinks; break;
+ case kpidSize: if (data) prop = data->GetSize(); break;
+ case kpidPackSize: if (data) prop = data->GetPackSize(); break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream, const UInt64 *, IArchiveOpenCallback *callback)
+{
+ COM_TRY_BEGIN
+ {
+ OpenCallback = callback;
+ InStream = stream;
+ HRESULT res;
+ try
+ {
+ res = CDatabase::Open();
+ if (res == S_OK)
+ return S_OK;
+ }
+ catch(...)
+ {
+ Close();
+ throw;
+ }
+ Close();
+ return res;
+ }
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ ClearAndClose();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool testMode = (_aTestMode != 0);
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (allFilesMode)
+ numItems = Items.Size();
+ if (numItems == 0)
+ return S_OK;
+ UInt32 i;
+ UInt64 totalSize = 0;
+ for (i = 0; i < numItems; i++)
+ {
+ const CItem &item = Items[allFilesMode ? i : indices[i]];
+ const CMftRec &rec = Recs[item.RecIndex];
+ if (!rec.IsDir())
+ totalSize += rec.GetSize(item.DataIndex);
+ }
+ RINOK(extractCallback->SetTotal(totalSize));
+
+ UInt64 totalPackSize;
+ totalSize = totalPackSize = 0;
+
+ CByteBuffer buf;
+ UInt32 clusterSize = Header.ClusterSize();
+ buf.SetCapacity(clusterSize);
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
+
+ for (i = 0; i < numItems; i++)
+ {
+ lps->InSize = totalPackSize;
+ lps->OutSize = totalSize;
+ RINOK(lps->SetCur());
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ Int32 index = allFilesMode ? i : indices[i];
+ RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
+
+ const CItem &item = Items[index];
+ if (item.IsDir())
+ {
+ RINOK(extractCallback->PrepareOperation(askMode));
+ RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
+ continue;
+ }
+
+ if (!testMode && (!realOutStream))
+ continue;
+ RINOK(extractCallback->PrepareOperation(askMode));
+
+ outStreamSpec->SetStream(realOutStream);
+ realOutStream.Release();
+ outStreamSpec->Init();
+
+ const CMftRec &rec = Recs[item.RecIndex];
+ const CAttr &data = rec.DataAttrs[rec.DataRefs[item.DataIndex].Start];
+
+ int res = NArchive::NExtract::NOperationResult::kDataError;
+ {
+ CMyComPtr<IInStream> inStream;
+ HRESULT hres = rec.GetStream(InStream, item.DataIndex, Header.ClusterSizeLog, Header.NumClusters, &inStream);
+ if (hres == S_FALSE)
+ res = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
+ else
+ {
+ RINOK(hres);
+ if (inStream)
+ {
+ HRESULT hres = copyCoder->Code(inStream, outStream, NULL, NULL, progress);
+ if (hres != S_OK && hres != S_FALSE)
+ {
+ RINOK(hres);
+ }
+ if (/* copyCoderSpec->TotalSize == item.GetSize() && */ hres == S_OK)
+ res = NArchive::NExtract::NOperationResult::kOK;
+ }
+ }
+ }
+ totalPackSize += data.GetPackSize();
+ totalSize += data.GetSize();
+ outStreamSpec->ReleaseStream();
+ RINOK(extractCallback->SetOperationResult(res));
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = Items.Size();
+ return S_OK;
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"NTFS", L"ntfs img", 0, 0xD9, { 'N', 'T', 'F', 'S', ' ', ' ', ' ', ' ', 0 }, 9, false, CreateArc, 0 };
+
+REGISTER_ARC(Fat)
+
+}}
diff --git a/CPP/7zip/Archive/PeHandler.cpp b/CPP/7zip/Archive/PeHandler.cpp
index 70af37c7..a1304ae4 100755
--- a/CPP/7zip/Archive/PeHandler.cpp
+++ b/CPP/7zip/Archive/PeHandler.cpp
@@ -18,8 +18,6 @@
#include "../Compress/CopyCoder.h"
-#include "Common/DummyOutStream.h"
-
#define Get16(p) GetUi16(p)
#define Get32(p) GetUi32(p)
#define Get64(p) GetUi64(p)
@@ -549,11 +547,6 @@ STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
case kpidStackCommit: prop = _optHeader.StackCommit; break;
case kpidHeapReserve: prop = _optHeader.HeapReserve; break;
case kpidHeapCommit: prop = _optHeader.HeapCommit; break;
-
- /*
- if (_optHeader.Is64Bit())
- s += " 64-bit";
- */
}
prop.Detach(value);
return S_OK;
@@ -785,8 +778,6 @@ HRESULT CalcCheckSum(ISequentialInStream *stream, UInt32 size, UInt32 excludePos
RINOK(ReadStream(stream, buf, &processed));
/*
- */
- /*
for (; processed < rem; processed++)
buf[processed] = 0;
*/
@@ -880,9 +871,6 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CMyComPtr<ISequentialInStream> inStream(streamSpec);
streamSpec->SetStream(_inStream);
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
- CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
-
for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
{
lps->InSize = lps->OutSize = currentTotalSize;
@@ -893,20 +881,17 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
UInt32 index = allFilesMode ? i : indices[i];
const CSection &item = _sections[index];
currentItemSize = item.GetPackSize();
- {
- CMyComPtr<ISequentialOutStream> realOutStream;
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- if (!testMode && (!realOutStream))
- continue;
- outStreamSpec->SetStream(realOutStream);
- outStreamSpec->Init();
- }
+
+ CMyComPtr<ISequentialOutStream> outStream;
+ RINOK(extractCallback->GetStream(index, &outStream, askMode));
+ if (!testMode && !outStream)
+ continue;
RINOK(extractCallback->PrepareOperation(askMode));
RINOK(_inStream->Seek(item.Pa, STREAM_SEEK_SET, NULL));
streamSpec->Init(currentItemSize);
RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
- outStreamSpec->ReleaseStream();
+ outStream.Release();
RINOK(extractCallback->SetOperationResult((copyCoderSpec->TotalSize == currentItemSize) ?
checkSumOK ?
NArchive::NExtract::NOperationResult::kOK:
diff --git a/CPP/7zip/Archive/Rar/RarHandler.cpp b/CPP/7zip/Archive/Rar/RarHandler.cpp
index 2431e449..93c19265 100755
--- a/CPP/7zip/Archive/Rar/RarHandler.cpp
+++ b/CPP/7zip/Archive/Rar/RarHandler.cpp
@@ -251,7 +251,10 @@ public:
}
else if (!_newStyle)
{
- if (ext.CompareNoCase(L"000") == 0 || ext.CompareNoCase(L"001") == 0)
+ if (ext.CompareNoCase(L"000") == 0 ||
+ ext.CompareNoCase(L"001") == 0 ||
+ ext.CompareNoCase(L"r00") == 0 ||
+ ext.CompareNoCase(L"r01") == 0)
{
_afterPart.Empty();
_first = false;
diff --git a/CPP/7zip/Archive/Rar/RarIn.cpp b/CPP/7zip/Archive/Rar/RarIn.cpp
index 18669405..4810649b 100755
--- a/CPP/7zip/Archive/Rar/RarIn.cpp
+++ b/CPP/7zip/Archive/Rar/RarIn.cpp
@@ -2,19 +2,17 @@
#include "StdAfx.h"
+#include "../../../../C/7zCrc.h"
+
#include "Common/StringConvert.h"
#include "Common/UTFConvert.h"
-#include "RarIn.h"
#include "../../Common/LimitedStreams.h"
#include "../../Common/StreamUtils.h"
#include "../Common/FindSignature.h"
-extern "C"
-{
- #include "../../../../C/7zCrc.h"
-}
+#include "RarIn.h"
namespace NArchive {
namespace NRar {
diff --git a/CPP/7zip/Archive/Rar/RarVolumeInStream.cpp b/CPP/7zip/Archive/Rar/RarVolumeInStream.cpp
index 1845e20a..25194f91 100755
--- a/CPP/7zip/Archive/Rar/RarVolumeInStream.cpp
+++ b/CPP/7zip/Archive/Rar/RarVolumeInStream.cpp
@@ -2,15 +2,9 @@
#include "StdAfx.h"
-#include "RarVolumeInStream.h"
-
-#include "Windows/Defs.h"
-#include "Common/Defs.h"
+#include "../../../../C/7zCrc.h"
-extern "C"
-{
- #include "../../../../C/7zCrc.h"
-}
+#include "RarVolumeInStream.h"
namespace NArchive {
namespace NRar {
diff --git a/CPP/7zip/Archive/RpmHandler.cpp b/CPP/7zip/Archive/RpmHandler.cpp
index c6951799..13b67390 100755
--- a/CPP/7zip/Archive/RpmHandler.cpp
+++ b/CPP/7zip/Archive/RpmHandler.cpp
@@ -9,6 +9,7 @@
#include "Windows/PropVariant.h"
+#include "../Common/LimitedStreams.h"
#include "../Common/ProgressUtils.h"
#include "../Common/RegisterArc.h"
#include "../Common/StreamUtils.h"
@@ -113,23 +114,23 @@ HRESULT OpenArchive(IInStream *inStream)
return S_FALSE;
CSigHeaderSig sigHeader, header;
- if(lead.SignatureType == RPMSIG_NONE)
+ if (lead.SignatureType == RPMSIG_NONE)
{
;
}
- else if(lead.SignatureType == RPMSIG_PGP262_1024)
+ else if (lead.SignatureType == RPMSIG_PGP262_1024)
{
UInt64 pos;
RINOK(inStream->Seek(256, STREAM_SEEK_CUR, &pos));
}
- else if(lead.SignatureType == RPMSIG_HEADERSIG)
+ else if (lead.SignatureType == RPMSIG_HEADERSIG)
{
RINOK(RedSigHeaderSig(inStream, sigHeader));
- if(!sigHeader.MagicCheck())
+ if (!sigHeader.MagicCheck())
return S_FALSE;
UInt32 len = sigHeader.GetLostHeaderLen();
RINOK(inStream->Seek(len, STREAM_SEEK_CUR, &pos));
- if((pos % 8) != 0)
+ if ((pos % 8) != 0)
{
RINOK(inStream->Seek((pos / 8 + 1) * 8 - pos,
STREAM_SEEK_CUR, &pos));
@@ -139,10 +140,10 @@ HRESULT OpenArchive(IInStream *inStream)
return S_FALSE;
RINOK(RedSigHeaderSig(inStream, header));
- if(!header.MagicCheck())
+ if (!header.MagicCheck())
return S_FALSE;
int headerLen = header.GetLostHeaderLen();
- if(headerLen == -1)
+ if (headerLen == -1)
return S_FALSE;
RINOK(inStream->Seek(headerLen, STREAM_SEEK_CUR, &pos));
return S_OK;
@@ -150,28 +151,34 @@ HRESULT OpenArchive(IInStream *inStream)
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
+ CMyComPtr<IInStream> _stream;
+ UInt64 _pos;
+ UInt64 _size;
+ Byte _sig[4];
public:
- MY_UNKNOWN_IMP1(IInArchive)
-
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
INTERFACE_IInArchive(;)
-
-private:
- CMyComPtr<IInStream> m_InStream;
- UInt64 m_Pos;
- UInt64 m_Size;
- Byte _sig[4];
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
STATPROPSTG kProps[] =
{
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8}
+ { NULL, kpidSize, VT_UI8}
};
IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID) { case kpidMainSubfile: prop = (UInt32)0; break; }
+ prop.Detach(value);
+ return S_OK;
+}
STDMETHODIMP CHandler::Open(IInStream *inStream,
const UInt64 * /* maxCheckStartPosition */,
@@ -180,29 +187,24 @@ STDMETHODIMP CHandler::Open(IInStream *inStream,
COM_TRY_BEGIN
try
{
- if(OpenArchive(inStream) != S_OK)
+ Close();
+ if (OpenArchive(inStream) != S_OK)
return S_FALSE;
- RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Pos));
+ RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &_pos));
+ RINOK(ReadStream_FALSE(inStream, _sig, sizeof(_sig) / sizeof(_sig[0])));
UInt64 endPosition;
RINOK(inStream->Seek(0, STREAM_SEEK_END, &endPosition));
- m_Size = endPosition - m_Pos;
-
- RINOK(inStream->Seek(m_Pos, STREAM_SEEK_SET, NULL));
- RINOK(ReadStream_FALSE(inStream, _sig, sizeof(_sig) / sizeof(_sig[0])));
-
- m_InStream = inStream;
+ _size = endPosition - _pos;
+ _stream = inStream;
return S_OK;
}
- catch(...)
- {
- return S_FALSE;
- }
+ catch(...) { return S_FALSE; }
COM_TRY_END
}
STDMETHODIMP CHandler::Close()
{
- m_InStream.Release();
+ _stream.Release();
return S_OK;
}
@@ -219,19 +221,19 @@ STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIAN
{
case kpidSize:
case kpidPackSize:
- prop = m_Size;
+ prop = _size;
break;
case kpidExtension:
{
- wchar_t s[32];
- MyStringCopy(s, L"cpio.");
- const wchar_t *ext;
+ char s[32];
+ MyStringCopy(s, "cpio.");
+ const char *ext;
if (_sig[0] == 0x1F && _sig[1] == 0x8B)
- ext = L"gz";
+ ext = "gz";
else if (_sig[0] == 'B' && _sig[1] == 'Z' && _sig[2] == 'h')
- ext = L"bz2";
+ ext = "bz2";
else
- ext = L"lzma";
+ ext = "lzma";
MyStringCopy(s + MyStringLen(s), ext);
prop = s;
break;
@@ -245,58 +247,50 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
{
COM_TRY_BEGIN
- bool allFilesMode = (numItems == UInt32(-1));
- if (allFilesMode)
+ if (numItems == UInt32(-1))
numItems = 1;
- if(numItems == 0)
+ if (numItems == 0)
return S_OK;
- if(numItems != 1)
- return E_FAIL;
- if (indices[0] != 0)
- return E_FAIL;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
bool testMode = (_aTestMode != 0);
-
- UInt64 currentTotalSize = 0;
- RINOK(extractCallback->SetTotal(m_Size));
- RINOK(extractCallback->SetCompleted(&currentTotalSize));
- CMyComPtr<ISequentialOutStream> realOutStream;
+
+ RINOK(extractCallback->SetTotal(_size));
+ CMyComPtr<ISequentialOutStream> outStream;
Int32 askMode = testMode ?
NArchive::NExtract::NAskMode::kTest :
NArchive::NExtract::NAskMode::kExtract;
- Int32 index = 0;
-
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
-
- if(!testMode && (!realOutStream))
+ RINOK(extractCallback->GetStream(0, &outStream, askMode));
+ if (!testMode && !outStream)
return S_OK;
-
RINOK(extractCallback->PrepareOperation(askMode));
- if (testMode)
- {
- RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
- return S_OK;
- }
-
- RINOK(m_InStream->Seek(m_Pos, STREAM_SEEK_SET, NULL));
-
+
CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
CLocalProgress *lps = new CLocalProgress;
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(extractCallback, false);
- RINOK(copyCoder->Code(m_InStream, realOutStream, NULL, NULL, progress));
- realOutStream.Release();
+ RINOK(_stream->Seek(_pos, STREAM_SEEK_SET, NULL));
+ RINOK(copyCoder->Code(_stream, outStream, NULL, NULL, progress));
+ outStream.Release();
return extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK);
COM_TRY_END
}
+STDMETHODIMP CHandler::GetStream(UInt32 /* index */, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ return CreateLimitedInStream(_stream, _pos, _size, stream);
+ COM_TRY_END
+}
+
static IInArchive *CreateArc() { return new NArchive::NRpm::CHandler; }
static CArcInfo g_ArcInfo =
- { L"Rpm", L"rpm", 0, 0xEB, { 0}, 0, false, CreateArc, 0 };
+ { L"Rpm", L"rpm", 0, 0xEB, { 0xED, 0xAB, 0xEE, 0xDB}, 4, false, CreateArc, 0 };
REGISTER_ARC(Rpm)
diff --git a/CPP/7zip/Archive/Split/SplitHandler.h b/CPP/7zip/Archive/Split/SplitHandler.h
deleted file mode 100755
index 9e020763..00000000
--- a/CPP/7zip/Archive/Split/SplitHandler.h
+++ /dev/null
@@ -1,37 +0,0 @@
-// Split/Handler.h
-
-#ifndef __SPLIT_HANDLER_H
-#define __SPLIT_HANDLER_H
-
-#include "Common/MyCom.h"
-#include "Common/MyString.h"
-#include "../IArchive.h"
-
-namespace NArchive {
-namespace NSplit {
-
-class CHandler:
- public IInArchive,
- public IInArchiveGetStream,
- // public IOutArchive,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
-
- INTERFACE_IInArchive(;)
-
- STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
-
-private:
- UString _subName;
- UString _name;
- CObjectVector<CMyComPtr<IInStream> > _streams;
- CRecordVector<UInt64> _sizes;
-
- UInt64 _totalSize;
-};
-
-}}
-
-#endif
diff --git a/CPP/7zip/Archive/Split/SplitHandlerOut.cpp b/CPP/7zip/Archive/Split/SplitHandlerOut.cpp
deleted file mode 100755
index 6edf86f4..00000000
--- a/CPP/7zip/Archive/Split/SplitHandlerOut.cpp
+++ /dev/null
@@ -1,102 +0,0 @@
-// Split/OutHandler.cpp
-
-#include "StdAfx.h"
-
-#include "SplitHandler.h"
-#include "../../../Windows/PropVariant.h"
-#include "../../../Common/ComTry.h"
-#include "../../../Common/StringToInt.h"
-
-using namespace NWindows;
-
-namespace NArchive {
-namespace NSplit {
-
-/*
-STDMETHODIMP CHandler::GetFileTimeType(UInt32 *type)
-{
- *type = NFileTimeType::kWindows;
- return S_OK;
-}
-
-STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
- IArchiveUpdateCallback *updateCallback)
-{
- COM_TRY_BEGIN
-
- if (numItems != 1)
- return E_INVALIDARG;
-
- UInt64 volumeSize = 0;
-
- CMyComPtr<IArchiveUpdateCallback2> callback2;
- updateCallback->QueryInterface(IID_IArchiveUpdateCallback2,
- (void **)&callback2);
-
- RINOK(callback2->GetVolumeSize(0, &volumeSize));
-
- Int32 newData;
- Int32 newProperties;
- UInt32 indexInArchive;
- if (!updateCallback)
- return E_FAIL;
-
- UInt32 fileIndex = 0;
- RINOK(updateCallback->GetUpdateItemInfo(fileIndex,
- &newData, &newProperties, &indexInArchive));
-
- if (newProperties != 0)
- {
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(fileIndex, kpidIsFolder, &prop));
- if (prop.vt == VT_EMPTY)
- {
- }
- else if (prop.vt != VT_BOOL)
- return E_INVALIDARG;
- else
- {
- if (prop.boolVal != VARIANT_FALSE)
- return E_INVALIDARG;
- }
- }
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(fileIndex, kpidIsAnti, &prop));
- if (prop.vt == VT_EMPTY)
- {
- }
- else if (prop.vt != VT_BOOL)
- return E_INVALIDARG;
- else
- {
- if (prop.boolVal != VARIANT_FALSE)
- return E_INVALIDARG;
- }
- }
- }
- UInt64 newSize;
- bool thereIsCopyData = false;
- if (newData != 0)
- {
- NCOM::CPropVariant prop;
- RINOK(updateCallback->GetProperty(fileIndex, kpidSize, &prop));
- if (prop.vt != VT_UI8)
- return E_INVALIDARG;
- newSize = prop.uhVal.QuadPart;
- }
- else
- thereIsCopyData = true;
-
- UInt64 pos = 0;
- while(pos < newSize)
- {
-
- }
- return S_OK;
- COM_TRY_END
-}
-*/
-
-}}
diff --git a/CPP/7zip/Archive/Split/SplitRegister.cpp b/CPP/7zip/Archive/Split/SplitRegister.cpp
deleted file mode 100755
index 56ddba29..00000000
--- a/CPP/7zip/Archive/Split/SplitRegister.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
-// SplitRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../../Common/RegisterArc.h"
-
-#include "SplitHandler.h"
-static IInArchive *CreateArc() { return new NArchive::NSplit::CHandler; }
-/*
-#ifndef EXTRACT_ONLY
-static IOutArchive *CreateArcOut() { return new NArchive::NSplit::CHandler; }
-#else
-#define CreateArcOut 0
-#endif
-*/
-
-static CArcInfo g_ArcInfo =
-{ L"Split", L"001", 0, 0xEA, { 0 }, 0, false, CreateArc, 0 };
-
-REGISTER_ARC(Split)
diff --git a/CPP/7zip/Archive/Split/StdAfx.h b/CPP/7zip/Archive/Split/StdAfx.h
deleted file mode 100755
index e7fb6986..00000000
--- a/CPP/7zip/Archive/Split/StdAfx.h
+++ /dev/null
@@ -1,8 +0,0 @@
-// StdAfx.h
-
-#ifndef __STDAFX_H
-#define __STDAFX_H
-
-#include "../../../Common/MyWindows.h"
-
-#endif
diff --git a/CPP/7zip/Archive/Split/SplitHandler.cpp b/CPP/7zip/Archive/SplitHandler.cpp
index 61b7f4a7..892e12af 100755
--- a/CPP/7zip/Archive/Split/SplitHandler.cpp
+++ b/CPP/7zip/Archive/SplitHandler.cpp
@@ -3,24 +3,18 @@
#include "StdAfx.h"
#include "Common/ComTry.h"
-#include "Common/Defs.h"
-#include "Common/NewHandler.h"
-#include "Common/StringConvert.h"
+#include "Common/MyString.h"
#include "Windows/PropVariant.h"
-#include "Windows/Time.h"
-#include "../../Common/ProgressUtils.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
-#include "../../Compress/CopyCoder.h"
+#include "../Compress/CopyCoder.h"
-#include "../Common/ItemNameUtils.h"
-#include "../Common/MultiStream.h"
-
-#include "SplitHandler.h"
+#include "Common/MultiStream.h"
using namespace NWindows;
-using namespace NTime;
namespace NArchive {
namespace NSplit {
@@ -28,19 +22,50 @@ namespace NSplit {
STATPROPSTG kProps[] =
{
{ NULL, kpidPath, VT_BSTR},
- { NULL, kpidSize, VT_UI8},
- { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidSize, VT_UI8}
};
-IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
+STATPROPSTG kArcProps[] =
+{
+ { NULL, kpidNumVolumes, VT_UI4}
+};
-class CSeqName
+class CHandler:
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp
{
+ UString _subName;
+ CObjectVector<CMyComPtr<IInStream> > _streams;
+ CRecordVector<UInt64> _sizes;
+ UInt64 _totalSize;
public:
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidMainSubfile: prop = (UInt32)0; break;
+ case kpidNumVolumes: prop = (UInt32)_streams.Size(); break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
+
+struct CSeqName
+{
UString _unchangedPart;
UString _changedPart;
bool _splitStyle;
+
UString GetNextName()
{
UString newName;
@@ -125,23 +150,24 @@ STDMETHODIMP CHandler::Open(IInStream *stream,
&openVolumeCallback) != S_OK)
return S_FALSE;
+ UString name;
{
NCOM::CPropVariant prop;
RINOK(openVolumeCallback->GetProperty(kpidName, &prop));
if (prop.vt != VT_BSTR)
return S_FALSE;
- _name = prop.bstrVal;
+ name = prop.bstrVal;
}
- int dotPos = _name.ReverseFind('.');
+ int dotPos = name.ReverseFind('.');
UString prefix, ext;
if (dotPos >= 0)
{
- prefix = _name.Left(dotPos + 1);
- ext = _name.Mid(dotPos + 1);
+ prefix = name.Left(dotPos + 1);
+ ext = name.Mid(dotPos + 1);
}
else
- ext = _name;
+ ext = name;
UString extBig = ext;
extBig.MakeUpper();
@@ -258,9 +284,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIAN
NWindows::NCOM::CPropVariant prop;
switch(propID)
{
- case kpidPath:
- prop = _subName;
- break;
+ case kpidPath: prop = _subName; break;
case kpidSize:
case kpidPackSize:
prop = _totalSize;
@@ -271,48 +295,28 @@ STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIAN
}
STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
- Int32 _aTestMode, IArchiveExtractCallback *_anExtractCallback)
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
{
COM_TRY_BEGIN
+ if (numItems == UInt32(-1))
+ numItems = 1;
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
- if (numItems != UInt32(-1))
- {
- if (numItems != 1)
- return E_INVALIDARG;
- if (indices[0] != 0)
- return E_INVALIDARG;
- }
bool testMode = (_aTestMode != 0);
- CMyComPtr<IArchiveExtractCallback> extractCallback = _anExtractCallback;
- extractCallback->SetTotal(_totalSize);
-
- /*
- CMyComPtr<IArchiveVolumeExtractCallback> volumeExtractCallback;
- if (extractCallback.QueryInterface(&volumeExtractCallback) != S_OK)
- return E_FAIL;
- */
-
UInt64 currentTotalSize = 0;
- UInt64 currentItemSize;
-
- RINOK(extractCallback->SetCompleted(&currentTotalSize));
- CMyComPtr<ISequentialOutStream> realOutStream;
- Int32 askMode;
- askMode = testMode ? NArchive::NExtract::NAskMode::kTest :
- NArchive::NExtract::NAskMode::kExtract;
- Int32 index = 0;
- RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
-
- RINOK(extractCallback->PrepareOperation(askMode));
- if (testMode)
- {
- RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
+ RINOK(extractCallback->SetTotal(_totalSize));
+ CMyComPtr<ISequentialOutStream> outStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ RINOK(extractCallback->GetStream(0, &outStream, askMode));
+ if (!testMode && !outStream)
return S_OK;
- }
+ RINOK(extractCallback->PrepareOperation(askMode));
- if (!testMode && (!realOutStream))
- return S_OK;
-
NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder;
CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
@@ -320,22 +324,23 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(extractCallback, false);
- for (int i = 0; i < _streams.Size(); i++, currentTotalSize += currentItemSize)
+ for (int i = 0; i < _streams.Size(); i++)
{
lps->InSize = lps->OutSize = currentTotalSize;
RINOK(lps->SetCur());
IInStream *inStream = _streams[i];
RINOK(inStream->Seek(0, STREAM_SEEK_SET, NULL));
- RINOK(copyCoder->Code(inStream, realOutStream, NULL, NULL, progress));
- currentItemSize = copyCoderSpec->TotalSize;
+ RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ currentTotalSize += copyCoderSpec->TotalSize;
}
- realOutStream.Release();
+ outStream.Release();
return extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK);
COM_TRY_END
}
STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
{
+ COM_TRY_BEGIN
if (index != 0)
return E_INVALIDARG;
*stream = 0;
@@ -352,6 +357,14 @@ STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
streamSpec->Init();
*stream = streamTemp.Detach();
return S_OK;
+ COM_TRY_END
}
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+{ L"Split", L"001", 0, 0xEA, { 0 }, 0, false, CreateArc, 0 };
+
+REGISTER_ARC(Split)
+
}}
diff --git a/CPP/7zip/Archive/Tar/TarHandler.cpp b/CPP/7zip/Archive/Tar/TarHandler.cpp
index f8000c85..aa4b2aec 100755
--- a/CPP/7zip/Archive/Tar/TarHandler.cpp
+++ b/CPP/7zip/Archive/Tar/TarHandler.cpp
@@ -13,9 +13,6 @@
#include "../../Common/LimitedStreams.h"
#include "../../Common/ProgressUtils.h"
-#include "../../Compress/CopyCoder.h"
-
-#include "../Common/DummyOutStream.h"
#include "../Common/ItemNameUtils.h"
#include "TarHandler.h"
@@ -33,22 +30,35 @@ STATPROPSTG kProps[] =
{ NULL, kpidSize, VT_UI8},
{ NULL, kpidPackSize, VT_UI8},
{ NULL, kpidMTime, VT_FILETIME},
+ { NULL, kpidPosixAttrib, VT_UI4},
{ NULL, kpidUser, VT_BSTR},
- { NULL, kpidGroup, VT_BSTR}
+ { NULL, kpidGroup, VT_BSTR},
+ { NULL, kpidLink, VT_BSTR}
};
IMP_IInArchive_Props
-IMP_IInArchive_ArcProps_NO
+IMP_IInArchive_ArcProps_NO_Table
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidPhySize: if (_phySizeDefined) prop = _phySize; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+}
HRESULT CHandler::Open2(IInStream *stream, IArchiveOpenCallback *callback)
{
UInt64 endPos = 0;
- if (callback != NULL)
{
RINOK(stream->Seek(0, STREAM_SEEK_END, &endPos));
RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
}
+ _isGood = true;
UInt64 pos = 0;
for (;;)
{
@@ -61,8 +71,13 @@ HRESULT CHandler::Open2(IInStream *stream, IArchiveOpenCallback *callback)
_items.Add(item);
RINOK(stream->Seek(item.GetPackSize(), STREAM_SEEK_CUR, &pos));
- if (pos >= endPos)
+ if (pos > endPos)
return S_FALSE;
+ if (pos == endPos)
+ {
+ _isGood = false;
+ break;
+ }
if (callback != NULL)
{
if (_items.Size() == 1)
@@ -98,70 +113,134 @@ HRESULT CHandler::Open2(IInStream *stream, IArchiveOpenCallback *callback)
return S_OK;
}
-STDMETHODIMP CHandler::Open(IInStream *stream,
- const UInt64 * /* maxCheckStartPosition */,
- IArchiveOpenCallback *openArchiveCallback)
+STDMETHODIMP CHandler::Open(IInStream *stream, const UInt64 *, IArchiveOpenCallback *openArchiveCallback)
{
COM_TRY_BEGIN
{
Close();
RINOK(Open2(stream, openArchiveCallback));
- _inStream = stream;
+ _stream = stream;
}
return S_OK;
COM_TRY_END
}
+STDMETHODIMP CHandler::OpenSeq(ISequentialInStream *stream)
+{
+ Close();
+ _seqStream = stream;
+ return S_OK;
+}
+
STDMETHODIMP CHandler::Close()
{
+ _phySizeDefined = false;
+ _curIndex = 0;
+ _latestIsRead = false;
_items.Clear();
- _inStream.Release();
+ _seqStream.Release();
+ _stream.Release();
return S_OK;
}
STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
{
- *numItems = _items.Size();
+ *numItems = (_stream ? _items.Size() : (UInt32)(Int32)-1);
+ return S_OK;
+}
+
+CHandler::CHandler()
+{
+ copyCoderSpec = new NCompress::CCopyCoder();
+ copyCoder = copyCoderSpec;
+}
+
+HRESULT CHandler::SkipTo(UInt32 index)
+{
+ while (_curIndex < index || !_latestIsRead)
+ {
+ if (_latestIsRead)
+ {
+ UInt64 packSize = _latestItem.GetPackSize();
+ RINOK(copyCoderSpec->Code(_seqStream, NULL, &packSize, &packSize, NULL));
+ _latestIsRead = false;
+ _curIndex++;
+ }
+ else
+ {
+ bool filled;
+ // item.HeaderPosition = pos;
+ RINOK(ReadItem(_seqStream, filled, _latestItem));
+ if (!filled)
+ return E_INVALIDARG;
+ _latestIsRead = true;
+ }
+ }
return S_OK;
}
+static UString TarStringToUnicode(const AString &s)
+{
+ return MultiByteToUnicodeString(s, CP_OEMCP);
+}
+
STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
{
COM_TRY_BEGIN
NWindows::NCOM::CPropVariant prop;
- const CItemEx &item = _items[index];
+
+ const CItemEx *item;
+ if (_stream)
+ item = &_items[index];
+ else
+ {
+ if (index < _curIndex)
+ return E_INVALIDARG;
+ else
+ {
+ RINOK(SkipTo(index));
+ item = &_latestItem;
+ }
+ }
switch(propID)
{
- case kpidPath: prop = NItemName::GetOSName2(MultiByteToUnicodeString(item.Name, CP_OEMCP)); break;
- case kpidIsDir: prop = item.IsDir(); break;
- case kpidSize: prop = item.Size; break;
- case kpidPackSize: prop = item.GetPackSize(); break;
+ case kpidPath: prop = NItemName::GetOSName2(TarStringToUnicode(item->Name)); break;
+ case kpidIsDir: prop = item->IsDir(); break;
+ case kpidSize: prop = item->Size; break;
+ case kpidPackSize: prop = item->GetPackSize(); break;
case kpidMTime:
- if (item.MTime != 0)
+ if (item->MTime != 0)
{
FILETIME ft;
- NTime::UnixTimeToFileTime(item.MTime, ft);
+ NTime::UnixTimeToFileTime(item->MTime, ft);
prop = ft;
}
break;
- case kpidUser: prop = MultiByteToUnicodeString(item.UserName, CP_OEMCP); break;
- case kpidGroup: prop = MultiByteToUnicodeString(item.GroupName, CP_OEMCP); break;
+ case kpidPosixAttrib: prop = item->Mode; break;
+ case kpidUser: prop = TarStringToUnicode(item->User); break;
+ case kpidGroup: prop = TarStringToUnicode(item->Group); break;
+ case kpidLink: prop = TarStringToUnicode(item->LinkName); break;
}
prop.Detach(value);
return S_OK;
COM_TRY_END
}
-STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+HRESULT CHandler::Extract(const UInt32* indices, UInt32 numItems,
Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
{
COM_TRY_BEGIN
+ ISequentialInStream *stream = _seqStream;
+ bool seqMode = (_stream == NULL);
+ if (!seqMode)
+ stream = _stream;
+
bool testMode = (_aTestMode != 0);
- bool allFilesMode = (numItems == UInt32(-1));
+ bool allFilesMode = (numItems == (UInt32)-1);
if (allFilesMode)
numItems = _items.Size();
- if (numItems == 0)
+ if (_stream && numItems == 0)
return S_OK;
UInt64 totalSize = 0;
UInt32 i;
@@ -169,24 +248,21 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
totalSize += _items[allFilesMode ? i : indices[i]].Size;
extractCallback->SetTotal(totalSize);
- UInt64 totalPackSize, curPackSize, curSize;
+ UInt64 totalPackSize;
totalSize = totalPackSize = 0;
- NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
- CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
-
CLocalProgress *lps = new CLocalProgress;
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(extractCallback, false);
CLimitedSequentialInStream *streamSpec = new CLimitedSequentialInStream;
CMyComPtr<ISequentialInStream> inStream(streamSpec);
- streamSpec->SetStream(_inStream);
+ streamSpec->SetStream(stream);
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CLimitedSequentialOutStream *outStreamSpec = new CLimitedSequentialOutStream;
CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
- for (i = 0; i < numItems; i++, totalSize += curSize, totalPackSize += curPackSize)
+ for (i = 0; i < numItems || seqMode; i++)
{
lps->InSize = totalPackSize;
lps->OutSize = totalSize;
@@ -196,29 +272,54 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
NArchive::NExtract::NAskMode::kTest :
NArchive::NExtract::NAskMode::kExtract;
Int32 index = allFilesMode ? i : indices[i];
- const CItemEx &item = _items[index];
+ const CItemEx *item;
+ if (seqMode)
+ {
+ HRESULT res = SkipTo(index);
+ if (res == E_INVALIDARG)
+ break;
+ RINOK(res);
+ item = &_latestItem;
+ }
+ else
+ item = &_items[index];
+
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
- curSize = item.Size;
- curPackSize = item.GetPackSize();
- if (item.IsDir())
+ totalSize += item->Size;
+ totalPackSize += item->GetPackSize();
+ if (item->IsDir())
{
RINOK(extractCallback->PrepareOperation(askMode));
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
continue;
}
- if (!testMode && (!realOutStream))
- continue;
+ bool skipMode = false;
+ if (!testMode && !realOutStream)
+ {
+ if (!seqMode)
+ continue;
+ skipMode = true;
+ askMode = NArchive::NExtract::NAskMode::kSkip;
+ }
RINOK(extractCallback->PrepareOperation(askMode));
outStreamSpec->SetStream(realOutStream);
realOutStream.Release();
- outStreamSpec->Init();
+ outStreamSpec->Init(skipMode ? 0 : item->Size, true);
- RINOK(_inStream->Seek(item.GetDataPosition(), STREAM_SEEK_SET, NULL));
- streamSpec->Init(item.Size);
+ if (!seqMode)
+ {
+ RINOK(_stream->Seek(item->GetDataPosition(), STREAM_SEEK_SET, NULL));
+ }
+ streamSpec->Init(item->GetPackSize());
RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
+ if (seqMode)
+ {
+ _latestIsRead = false;
+ _curIndex++;
+ }
outStreamSpec->ReleaseStream();
- RINOK(extractCallback->SetOperationResult(copyCoderSpec->TotalSize == item.Size ?
+ RINOK(extractCallback->SetOperationResult(outStreamSpec->GetRem() == 0 ?
NArchive::NExtract::NOperationResult::kOK:
NArchive::NExtract::NOperationResult::kDataError));
}
@@ -226,4 +327,12 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
COM_TRY_END
}
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ const CItemEx &item = _items[index];
+ return CreateLimitedInStream(_stream, item.GetDataPosition(), item.Size, stream);
+ COM_TRY_END
+}
+
}}
diff --git a/CPP/7zip/Archive/Tar/TarHandler.h b/CPP/7zip/Archive/Tar/TarHandler.h
index a98b5404..d2def9a1 100755
--- a/CPP/7zip/Archive/Tar/TarHandler.h
+++ b/CPP/7zip/Archive/Tar/TarHandler.h
@@ -1,4 +1,4 @@
-// Tar/Handler.h
+// TarHandler.h
#ifndef __TAR_HANDLER_H
#define __TAR_HANDLER_H
@@ -6,6 +6,8 @@
#include "Common/MyCom.h"
#include "../IArchive.h"
+#include "../../Compress/CopyCoder.h"
+
#include "TarItem.h"
namespace NArchive {
@@ -13,23 +15,43 @@ namespace NTar {
class CHandler:
public IInArchive,
+ public IArchiveOpenSeq,
+ public IInArchiveGetStream,
public IOutArchive,
public CMyUnknownImp
{
+ CObjectVector<CItemEx> _items;
+ CMyComPtr<IInStream> _stream;
+ CMyComPtr<ISequentialInStream> _seqStream;
+ bool _isGood;
+
+ UInt32 _curIndex;
+ bool _latestIsRead;
+ CItemEx _latestItem;
+
+ UInt64 _phySize;
+ bool _phySizeDefined;
+
+ NCompress::CCopyCoder *copyCoderSpec;
+ CMyComPtr<ICompressCoder> copyCoder;
+
+ HRESULT Open2(IInStream *stream, IArchiveOpenCallback *callback);
+ HRESULT SkipTo(UInt32 index);
+
public:
- MY_UNKNOWN_IMP2(
+ MY_UNKNOWN_IMP4(
IInArchive,
+ IArchiveOpenSeq,
+ IInArchiveGetStream,
IOutArchive
)
INTERFACE_IInArchive(;)
INTERFACE_IOutArchive(;)
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream);
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
- HRESULT Open2(IInStream *stream, IArchiveOpenCallback *callback);
-
-private:
- CObjectVector<CItemEx> _items;
- CMyComPtr<IInStream> _inStream;
+ CHandler();
};
}}
diff --git a/CPP/7zip/Archive/Tar/TarHandlerOut.cpp b/CPP/7zip/Archive/Tar/TarHandlerOut.cpp
index 3454868e..4c0cb5f8 100755
--- a/CPP/7zip/Archive/Tar/TarHandlerOut.cpp
+++ b/CPP/7zip/Archive/Tar/TarHandlerOut.cpp
@@ -1,20 +1,17 @@
-// Tar/HandlerOut.cpp
+// TarHandlerOut.cpp
#include "StdAfx.h"
-#include "Common/StringConvert.h"
#include "Common/ComTry.h"
+#include "Common/StringConvert.h"
#include "Windows/PropVariant.h"
#include "Windows/Time.h"
-#include "../Common/ItemNameUtils.h"
-
#include "TarHandler.h"
#include "TarUpdate.h"
using namespace NWindows;
-using namespace NCOM;
namespace NArchive {
namespace NTar {
@@ -25,94 +22,95 @@ STDMETHODIMP CHandler::GetFileTimeType(UInt32 *type)
return S_OK;
}
+static HRESULT GetPropString(IArchiveUpdateCallback *callback, UInt32 index, PROPID propId, AString &res)
+{
+ NCOM::CPropVariant prop;
+ RINOK(callback->GetProperty(index, propId, &prop));
+ if (prop.vt == VT_BSTR)
+ res = UnicodeStringToMultiByte(prop.bstrVal, CP_OEMCP);
+ else if (prop.vt != VT_EMPTY)
+ return E_INVALIDARG;
+ return S_OK;
+}
+
STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
IArchiveUpdateCallback *callback)
{
COM_TRY_BEGIN
+ if ((_stream && !_isGood) || _seqStream)
+ return E_NOTIMPL;
CObjectVector<CUpdateItem> updateItems;
for (UInt32 i = 0; i < numItems; i++)
{
CUpdateItem ui;
Int32 newData;
- Int32 newProperties;
+ Int32 newProps;
UInt32 indexInArchive;
if (!callback)
return E_FAIL;
- RINOK(callback->GetUpdateItemInfo(i, &newData, &newProperties, &indexInArchive));
- ui.NewProperties = IntToBool(newProperties);
+ RINOK(callback->GetUpdateItemInfo(i, &newData, &newProps, &indexInArchive));
+ ui.NewProps = IntToBool(newProps);
ui.NewData = IntToBool(newData);
ui.IndexInArchive = indexInArchive;
ui.IndexInClient = i;
- if (IntToBool(newProperties))
+ if (IntToBool(newProps))
{
- FILETIME utcTime;
- UString name;
- /*
- UInt32 attributes;
{
NCOM::CPropVariant prop;
- RINOK(callback->GetProperty(i, kpidAttrib, &prop));
+ RINOK(callback->GetProperty(i, kpidIsDir, &prop));
if (prop.vt == VT_EMPTY)
- attributes = 0;
- else if (prop.vt != VT_UI4)
+ ui.IsDir = false;
+ else if (prop.vt != VT_BOOL)
return E_INVALIDARG;
else
- attributes = prop.ulVal;
- }
- */
- {
- NCOM::CPropVariant prop;
- RINOK(callback->GetProperty(i, kpidMTime, &prop));
- if (prop.vt != VT_FILETIME)
- return E_INVALIDARG;
- utcTime = prop.filetime;
+ ui.IsDir = (prop.boolVal != VARIANT_FALSE);
}
+
{
NCOM::CPropVariant prop;
- RINOK(callback->GetProperty(i, kpidPath, &prop));
+ RINOK(callback->GetProperty(i, kpidPosixAttrib, &prop));
if (prop.vt == VT_EMPTY)
- name.Empty();
- else if (prop.vt != VT_BSTR)
+ ui.Mode = 0777 | (ui.IsDir ? 0040000 : 0100000);
+ else if (prop.vt != VT_UI4)
return E_INVALIDARG;
else
- name = prop.bstrVal;
+ ui.Mode = prop.ulVal;
}
{
NCOM::CPropVariant prop;
- RINOK(callback->GetProperty(i, kpidIsDir, &prop));
+ RINOK(callback->GetProperty(i, kpidMTime, &prop));
if (prop.vt == VT_EMPTY)
- ui.IsDir = false;
- else if (prop.vt != VT_BOOL)
+ ui.Time = 0;
+ else if (prop.vt != VT_FILETIME)
return E_INVALIDARG;
- else
- ui.IsDir = (prop.boolVal != VARIANT_FALSE);
+ else if (!NTime::FileTimeToUnixTime(prop.filetime, ui.Time))
+ ui.Time = 0;
}
- ui.Name = UnicodeStringToMultiByte(NItemName::MakeLegalName(name), CP_OEMCP);
- if (ui.IsDir)
- ui.Name += '/';
-
- if (!NTime::FileTimeToUnixTime(utcTime, ui.Time))
{
- ui.Time = 0;
- // return E_INVALIDARG;
+ NCOM::CPropVariant prop;
+ RINOK(callback->GetProperty(i, kpidPath, &prop));
+ if (prop.vt == VT_BSTR)
+ ui.Name = UnicodeStringToMultiByte(NItemName::MakeLegalName(prop.bstrVal), CP_OEMCP);
+ else if (prop.vt != VT_EMPTY)
+ return E_INVALIDARG;
+ if (ui.IsDir)
+ ui.Name += '/';
}
+ RINOK(GetPropString(callback, i, kpidUser, ui.User));
+ RINOK(GetPropString(callback, i, kpidGroup, ui.Group));
}
if (IntToBool(newData))
{
- UInt64 size;
- {
- NCOM::CPropVariant prop;
- RINOK(callback->GetProperty(i, kpidSize, &prop));
- if (prop.vt != VT_UI8)
- return E_INVALIDARG;
- size = prop.uhVal.QuadPart;
- }
- ui.Size = size;
+ NCOM::CPropVariant prop;
+ RINOK(callback->GetProperty(i, kpidSize, &prop));
+ if (prop.vt != VT_UI8)
+ return E_INVALIDARG;
+ ui.Size = prop.uhVal.QuadPart;
}
updateItems.Add(ui);
}
- return UpdateArchive(_inStream, outStream, _items, updateItems, callback);
+ return UpdateArchive(_stream, outStream, _items, updateItems, callback);
COM_TRY_END
}
diff --git a/CPP/7zip/Archive/Tar/TarIn.cpp b/CPP/7zip/Archive/Tar/TarIn.cpp
index 55215ac7..b8409195 100755
--- a/CPP/7zip/Archive/Tar/TarIn.cpp
+++ b/CPP/7zip/Archive/Tar/TarIn.cpp
@@ -1,15 +1,13 @@
-// Archive/TarIn.cpp
+// TarIn.cpp
#include "StdAfx.h"
-#include "TarIn.h"
-#include "TarHeader.h"
-
#include "Common/StringToInt.h"
-#include "Windows/Defs.h"
#include "../../Common/StreamUtils.h"
+#include "TarIn.h"
+
namespace NArchive {
namespace NTar {
@@ -98,8 +96,8 @@ static HRESULT GetNextItemReal(ISequentialInStream *stream, bool &filled, CItemE
memcpy(item.Magic, p, 8); p += 8;
- ReadString(p, NFileHeader::kUserNameSize, item.UserName); p += NFileHeader::kUserNameSize;
- ReadString(p, NFileHeader::kUserNameSize, item.GroupName); p += NFileHeader::kUserNameSize;
+ ReadString(p, NFileHeader::kUserNameSize, item.User); p += NFileHeader::kUserNameSize;
+ ReadString(p, NFileHeader::kGroupNameSize, item.Group); p += NFileHeader::kGroupNameSize;
item.DeviceMajorDefined = (p[0] != 0); RIF(OctalToNumber32(p, 8, item.DeviceMajor)); p += 8;
item.DeviceMinorDefined = (p[0] != 0); RIF(OctalToNumber32(p, 8, item.DeviceMinor)); p += 8;
@@ -132,7 +130,8 @@ HRESULT ReadItem(ISequentialInStream *stream, bool &filled, CItemEx &item)
if (!filled)
return S_OK;
// GNUtar extension
- if (item.LinkFlag == 'L')
+ if (item.LinkFlag == 'L' || // NEXT file has a long name
+ item.LinkFlag == 'K') // NEXT file has a long linkname
{
if (item.Name.Compare(NFileHeader::kLongLink) != 0)
if (item.Name.Compare(NFileHeader::kLongLink2) != 0)
@@ -150,11 +149,17 @@ HRESULT ReadItem(ISequentialInStream *stream, bool &filled, CItemEx &item)
fullName.ReleaseBuffer();
UInt64 headerPosition = item.HeaderPosition;
+ if (item.LinkFlag == 'L')
{
size_t processedSize2;
RINOK(GetNextItemReal(stream, filled, item, processedSize2));
+ item.LongLinkSize = (unsigned)processedSize;
+ }
+ else
+ {
+ item.LongLinkSize = (unsigned)processedSize - NFileHeader::kRecordSize;
+ item.Size = 0;
}
- item.LongLinkSize = (unsigned)processedSize;
item.Name = fullName;
item.HeaderPosition = headerPosition;
}
diff --git a/CPP/7zip/Archive/Tar/TarItem.h b/CPP/7zip/Archive/Tar/TarItem.h
index 7d95844d..afe8997d 100755
--- a/CPP/7zip/Archive/Tar/TarItem.h
+++ b/CPP/7zip/Archive/Tar/TarItem.h
@@ -1,12 +1,10 @@
-// Archive/Tar/Item.h
+// TarItem.h
#ifndef __ARCHIVE_TAR_ITEM_H
#define __ARCHIVE_TAR_ITEM_H
-#include "Common/Types.h"
-#include "Common/MyString.h"
-
#include "../Common/ItemNameUtils.h"
+
#include "TarHeader.h"
namespace NArchive {
@@ -25,8 +23,8 @@ struct CItem
UInt32 DeviceMinor;
AString LinkName;
- AString UserName;
- AString GroupName;
+ AString User;
+ AString Group;
char Magic[8];
char LinkFlag;
diff --git a/CPP/7zip/Archive/Tar/TarOut.cpp b/CPP/7zip/Archive/Tar/TarOut.cpp
index 0892748f..1ec314c7 100755
--- a/CPP/7zip/Archive/Tar/TarOut.cpp
+++ b/CPP/7zip/Archive/Tar/TarOut.cpp
@@ -1,14 +1,13 @@
-// Archive/TarOut.cpp
+// TarOut.cpp
#include "StdAfx.h"
-#include "TarOut.h"
-#include "TarHeader.h"
-
#include "Common/IntToString.h"
-#include "Windows/Defs.h"
+
#include "../../Common/StreamUtils.h"
+#include "TarOut.h"
+
namespace NArchive {
namespace NTar {
@@ -114,10 +113,10 @@ HRESULT COutArchive::WriteHeaderReal(const CItem &item)
memmove(cur, item.Magic, 8);
cur += 8;
- RETURN_IF_NOT_TRUE(CopyString(cur, item.UserName, NFileHeader::kUserNameSize));
- cur += NFileHeader::kUserNameSize;
- RETURN_IF_NOT_TRUE(CopyString(cur, item.GroupName, NFileHeader::kGroupNameSize));
+ RETURN_IF_NOT_TRUE(CopyString(cur, item.User, NFileHeader::kUserNameSize));
cur += NFileHeader::kUserNameSize;
+ RETURN_IF_NOT_TRUE(CopyString(cur, item.Group, NFileHeader::kGroupNameSize));
+ cur += NFileHeader::kGroupNameSize;
if (item.DeviceMajorDefined)
diff --git a/CPP/7zip/Archive/Tar/TarUpdate.cpp b/CPP/7zip/Archive/Tar/TarUpdate.cpp
index 1c048915..0577848f 100755
--- a/CPP/7zip/Archive/Tar/TarUpdate.cpp
+++ b/CPP/7zip/Archive/Tar/TarUpdate.cpp
@@ -55,10 +55,12 @@ HRESULT UpdateArchive(IInStream *inStream, ISequentialOutStream *outStream,
const CUpdateItem &ui = updateItems[i];
CItem item;
- if (ui.NewProperties)
+ if (ui.NewProps)
{
- item.Mode = 0777;
- item.Name = (ui.Name);
+ item.Mode = ui.Mode;
+ item.Name = ui.Name;
+ item.User = ui.User;
+ item.Group = ui.Group;
if (ui.IsDir)
{
item.LinkFlag = NFileHeader::NLinkFlag::kDirectory;
@@ -77,21 +79,16 @@ HRESULT UpdateArchive(IInStream *inStream, ISequentialOutStream *outStream,
memmove(item.Magic, NFileHeader::NMagic::kEmpty, 8);
}
else
- {
- const CItemEx &existItemInfo = inputItems[ui.IndexInArchive];
- item = existItemInfo;
- }
+ item = inputItems[ui.IndexInArchive];
+
if (ui.NewData)
{
item.Size = ui.Size;
- if (item.Size == UInt64(Int64(-1)))
+ if (item.Size == (UInt64)(Int64)-1)
return E_INVALIDARG;
}
else
- {
- const CItemEx &existItemInfo = inputItems[ui.IndexInArchive];
- item.Size = existItemInfo.Size;
- }
+ item.Size = inputItems[ui.IndexInArchive].Size;
if (ui.NewData)
{
@@ -116,7 +113,7 @@ HRESULT UpdateArchive(IInStream *inStream, ISequentialOutStream *outStream,
{
const CItemEx &existItemInfo = inputItems[ui.IndexInArchive];
UInt64 size;
- if (ui.NewProperties)
+ if (ui.NewProps)
{
RINOK(outArchive.WriteHeader(item));
RINOK(inStream->Seek(existItemInfo.GetDataPosition(), STREAM_SEEK_SET, NULL));
diff --git a/CPP/7zip/Archive/Tar/TarUpdate.h b/CPP/7zip/Archive/Tar/TarUpdate.h
index 7d196d1c..fb217d19 100755
--- a/CPP/7zip/Archive/Tar/TarUpdate.h
+++ b/CPP/7zip/Archive/Tar/TarUpdate.h
@@ -1,4 +1,4 @@
-// Tar/Update.h
+// TarUpdate.h
#ifndef __TAR_UPDATE_H
#define __TAR_UPDATE_H
@@ -11,14 +11,16 @@ namespace NTar {
struct CUpdateItem
{
- bool NewData;
- bool NewProperties;
int IndexInArchive;
int IndexInClient;
-
UInt32 Time;
+ UInt32 Mode;
UInt64 Size;
AString Name;
+ AString User;
+ AString Group;
+ bool NewData;
+ bool NewProps;
bool IsDir;
};
diff --git a/CPP/7zip/Archive/Udf/UdfHandler.cpp b/CPP/7zip/Archive/Udf/UdfHandler.cpp
index 12329147..07b61c51 100755
--- a/CPP/7zip/Archive/Udf/UdfHandler.cpp
+++ b/CPP/7zip/Archive/Udf/UdfHandler.cpp
@@ -8,12 +8,11 @@
#include "Windows/PropVariant.h"
#include "Windows/Time.h"
+#include "../../Common/LimitedStreams.h"
#include "../../Common/ProgressUtils.h"
#include "../../Compress/CopyCoder.h"
-#include "../Common/DummyOutStream.h"
-
#include "UdfHandler.h"
namespace NArchive {
@@ -201,79 +200,129 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
COM_TRY_END
}
-class CUdfInStream:
- public ISequentialInStream,
+class CBufInStream:
+ public IInStream,
public CMyUnknownImp
{
+ CByteBuffer _data;
+ UInt64 _pos;
+
+public:
+ void Init(const CByteBuffer &data)
+ {
+ _data = data;
+ _pos = 0;
+ }
+
MY_UNKNOWN_IMP
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
- UInt64 _rem;
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+
+STDMETHODIMP CBufInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_pos > _data.GetCapacity())
+ return E_FAIL;
+ size_t rem = _data.GetCapacity() - (size_t)_pos;
+ if (size < rem)
+ rem = (size_t)size;
+ memcpy(data, (const Byte *)_data + _pos, rem);
+ _pos += rem;
+ if (processedSize != NULL)
+ *processedSize = (UInt32)rem;
+ return S_OK;
+}
+
+STDMETHODIMP CBufInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: _pos = offset; break;
+ case STREAM_SEEK_CUR: _pos += offset; break;
+ case STREAM_SEEK_END: _pos = _data.GetCapacity() + offset; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (newPosition)
+ *newPosition = _pos;
+ return S_OK;
+}
+
+struct CSeekExtent
+{
+ UInt64 Phy;
+ UInt64 Virt;
+};
+
+class CExtentsStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+ UInt64 _phyPos;
+ UInt64 _virtPos;
+ bool _needStartSeek;
+
+ HRESULT SeekToPhys() { return Stream->Seek(_phyPos, STREAM_SEEK_SET, NULL); }
+
public:
- CInArchive *_archive;
- CMyComPtr<IInStream> _stream;
- CRef2 _ref2;
- int _extentIndex;
- UInt32 _offsetInExtent;
+ CMyComPtr<IInStream> Stream;
+ CRecordVector<CSeekExtent> Extents;
- void Init(UInt64 size)
+ MY_UNKNOWN_IMP1(IInStream)
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+ void ReleaseStream() { Stream.Release(); }
+
+ void Init()
{
- _extentIndex = 0;
- _offsetInExtent = 0;
- _rem = size;
+ _virtPos = 0;
+ _phyPos = 0;
+ _needStartSeek = true;
}
- void ReleaseStream() { _stream.Release(); }
+
};
-STDMETHODIMP CUdfInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+
+STDMETHODIMP CExtentsStream::Read(void *data, UInt32 size, UInt32 *processedSize)
{
if (processedSize)
*processedSize = 0;
- if (size > _rem)
- size = (UInt32)_rem;
- while (size > 0)
+ if (size > 0)
{
- const CLogVol &vol = _archive->LogVols[_ref2.Vol];
- const CRef &ref = vol.FileSets[_ref2.Fs].Refs[_ref2.Ref];
- const CFile &file = _archive->Files[ref.FileIndex];
- const CItem &item = _archive->Items[file.ItemIndex];
-
- HRESULT res = S_OK;
- if (item.IsInline)
+ UInt64 totalSize = Extents.Back().Virt;
+ if (_virtPos >= totalSize)
+ return (_virtPos == totalSize) ? S_OK : E_FAIL;
+ int left = 0, right = Extents.Size() - 1;
+ for (;;)
{
- size_t rem = item.InlineData.GetCapacity() - _offsetInExtent;
- if (rem == 0)
- return S_OK;
- if (rem > _rem)
- rem = (size_t)_rem;
- memcpy(data, (const Byte *)item.InlineData + _offsetInExtent, rem);
+ int mid = (left + right) / 2;
+ if (mid == left)
+ break;
+ if (_virtPos < Extents[mid].Virt)
+ right = mid;
+ else
+ left = mid;
}
- else
+
+ const CSeekExtent &extent = Extents[left];
+ UInt64 phyPos = extent.Phy + (_virtPos - extent.Virt);
+ if (_needStartSeek || _phyPos != phyPos)
{
- if (_extentIndex >= item.Extents.Size())
- return S_OK;
- const CMyExtent &extent = item.Extents[_extentIndex];
- UInt32 rem = extent.GetLen() - _offsetInExtent;
- if (rem == 0)
- {
- _extentIndex++;
- _offsetInExtent = 0;
- continue;
- }
- if (size > rem)
- size = rem;
-
- int partitionIndex = vol.PartitionMaps[extent.PartitionRef].PartitionIndex;
- UInt32 logBlockNumber = extent.Pos;
- const CPartition &partition = _archive->Partitions[partitionIndex];
- UInt64 offset = ((UInt64)partition.Pos << _archive->SecLogSize) +
- (UInt64)logBlockNumber * vol.BlockSize + _offsetInExtent;
-
- RINOK(_stream->Seek(offset, STREAM_SEEK_SET, NULL));
- res = _stream->Read(data, size, &size);
+ _needStartSeek = false;
+ _phyPos = phyPos;
+ RINOK(SeekToPhys());
}
- _offsetInExtent += size;
- _rem -= size;
+
+ UInt64 rem = Extents[left + 1].Virt - _virtPos;
+ if (size > rem)
+ size = (UInt32)rem;
+
+ HRESULT res = Stream->Read(data, size, &size);
+ _phyPos += size;
+ _virtPos += size;
if (processedSize)
*processedSize = size;
return res;
@@ -281,6 +330,83 @@ STDMETHODIMP CUdfInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
return S_OK;
}
+STDMETHODIMP CExtentsStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: _virtPos = offset; break;
+ case STREAM_SEEK_CUR: _virtPos += offset; break;
+ case STREAM_SEEK_END: _virtPos = Extents.Back().Virt + offset; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (newPosition)
+ *newPosition = _virtPos;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ *stream = 0;
+
+ const CRef2 &ref2 = _refs2[index];
+ const CLogVol &vol = _archive.LogVols[ref2.Vol];
+ const CRef &ref = vol.FileSets[ref2.Fs].Refs[ref2.Ref];
+ const CFile &file = _archive.Files[ref.FileIndex];
+ const CItem &item = _archive.Items[file.ItemIndex];
+ UInt64 size = item.Size;
+
+ if (!item.IsRecAndAlloc() || !item.CheckChunkSizes() || ! _archive.CheckItemExtents(ref2.Vol, item))
+ return E_NOTIMPL;
+
+ if (item.IsInline)
+ {
+ CBufInStream *inStreamSpec = new CBufInStream;
+ CMyComPtr<ISequentialInStream> inStream = inStreamSpec;
+ inStreamSpec->Init(item.InlineData);
+ *stream = inStream .Detach();
+ return S_OK;
+ }
+
+ CExtentsStream *extentStreamSpec = new CExtentsStream();
+ CMyComPtr<ISequentialInStream> extentStream = extentStreamSpec;
+
+ extentStreamSpec->Stream = _inStream;
+
+ UInt64 virtOffset = 0;
+ for (int extentIndex = 0; extentIndex < item.Extents.Size(); extentIndex++)
+ {
+ const CMyExtent &extent = item.Extents[extentIndex];
+ UInt32 len = extent.GetLen();
+ if (len == 0)
+ continue;
+ if (size < len)
+ return S_FALSE;
+
+ int partitionIndex = vol.PartitionMaps[extent.PartitionRef].PartitionIndex;
+ UInt32 logBlockNumber = extent.Pos;
+ const CPartition &partition = _archive.Partitions[partitionIndex];
+ UInt64 offset = ((UInt64)partition.Pos << _archive.SecLogSize) +
+ (UInt64)logBlockNumber * vol.BlockSize;
+
+ CSeekExtent se;
+ se.Phy = offset;
+ se.Virt = virtOffset;
+ virtOffset += len;
+ extentStreamSpec->Extents.Add(se);
+
+ size -= len;
+ }
+ if (size != 0)
+ return S_FALSE;
+ CSeekExtent se;
+ se.Phy = 0;
+ se.Virt = virtOffset;
+ extentStreamSpec->Extents.Add(se);
+ extentStreamSpec->Init();
+ *stream = extentStream.Detach();
+ return S_OK;
+}
+
STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
{
@@ -307,7 +433,6 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
extractCallback->SetTotal(totalSize);
UInt64 currentTotalSize = 0;
- UInt64 currentItemSize;
NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
@@ -316,20 +441,13 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
CMyComPtr<ICompressProgressInfo> progress = lps;
lps->Init(extractCallback, false);
- CUdfInStream *udfInStreamSpec = new CUdfInStream();
- CMyComPtr<ISequentialInStream> udfInStream = udfInStreamSpec;
-
- udfInStreamSpec->_archive = &_archive;
- udfInStreamSpec->_stream = _inStream;
-
- CDummyOutStream *outStreamSpec = new CDummyOutStream;
+ CLimitedSequentialOutStream *outStreamSpec = new CLimitedSequentialOutStream;
CMyComPtr<ISequentialOutStream> outStream(outStreamSpec);
- for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize)
+ for (i = 0; i < numItems; i++)
{
lps->InSize = lps->OutSize = currentTotalSize;
RINOK(lps->SetCur());
- currentItemSize = 0;
CMyComPtr<ISequentialOutStream> realOutStream;
Int32 askMode = testMode ?
NArchive::NExtract::NAskMode::kTest :
@@ -349,24 +467,28 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK));
continue;
}
- currentItemSize = item.Size;
+ currentTotalSize += item.Size;
- if (!testMode && (!realOutStream))
+ if (!testMode && !realOutStream)
continue;
- RINOK(extractCallback->PrepareOperation(askMode));
+ RINOK(extractCallback->PrepareOperation(askMode));
outStreamSpec->SetStream(realOutStream);
realOutStream.Release();
- outStreamSpec->Init();
- Int32 opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
- if (item.IsRecAndAlloc() && item.CheckChunkSizes() && _archive.CheckItemExtents(ref2.Vol, item))
+ outStreamSpec->Init(item.Size);
+ Int32 opRes;
+ CMyComPtr<ISequentialInStream> udfInStream;
+ HRESULT res = GetStream(index, &udfInStream);
+ if (res == E_NOTIMPL)
+ opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
+ else if (res != S_OK)
+ opRes = NArchive::NExtract::NOperationResult::kDataError;
+ else
{
- udfInStreamSpec->_ref2 = ref2;
- udfInStreamSpec->Init(item.Size);
RINOK(copyCoder->Code(udfInStream, outStream, NULL, NULL, progress));
- opRes = (outStreamSpec->GetSize() == currentItemSize) ?
- NArchive::NExtract::NOperationResult::kOK:
- NArchive::NExtract::NOperationResult::kDataError;
+ opRes = outStreamSpec->IsFinishedOK() ?
+ NArchive::NExtract::NOperationResult::kOK:
+ NArchive::NExtract::NOperationResult::kDataError;
}
outStreamSpec->ReleaseStream();
RINOK(extractCallback->SetOperationResult(opRes));
diff --git a/CPP/7zip/Archive/Udf/UdfHandler.h b/CPP/7zip/Archive/Udf/UdfHandler.h
index ceab85ae..63f859af 100755
--- a/CPP/7zip/Archive/Udf/UdfHandler.h
+++ b/CPP/7zip/Archive/Udf/UdfHandler.h
@@ -20,14 +20,16 @@ struct CRef2
class CHandler:
public IInArchive,
+ public IInArchiveGetStream,
public CMyUnknownImp
{
CMyComPtr<IInStream> _inStream;
CInArchive _archive;
CRecordVector<CRef2> _refs2;
public:
- MY_UNKNOWN_IMP1(IInArchive)
+ MY_UNKNOWN_IMP2(IInArchive, IInArchiveGetStream)
INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
};
}}
diff --git a/CPP/7zip/Archive/Udf/UdfIn.cpp b/CPP/7zip/Archive/Udf/UdfIn.cpp
index 75a0c333..d2f9e731 100755
--- a/CPP/7zip/Archive/Udf/UdfIn.cpp
+++ b/CPP/7zip/Archive/Udf/UdfIn.cpp
@@ -2,14 +2,11 @@
#include "StdAfx.h"
-#include "UdfIn.h"
+#include "../../../../C/CpuArch.h"
#include "../../Common/StreamUtils.h"
-extern "C"
-{
- #include "../../../../C/CpuArch.h"
-}
+#include "UdfIn.h"
#define Get16(p) GetUi16(p)
#define Get32(p) GetUi32(p)
@@ -580,11 +577,16 @@ HRESULT CInArchive::Open2()
UInt64 fileSize;
RINOK(_stream->Seek(0, STREAM_SEEK_END, &fileSize));
- const int kSecLogSizeMax = 11;
- const int kSecLogSizeMin = 8;
+ // Some UDFs contain additional 2 KB of zeros, so we also check 12, corrected to 11.
+ const int kSecLogSizeMax = 12;
Byte buf[1 << kSecLogSizeMax];
- for (SecLogSize = kSecLogSizeMax; SecLogSize >= kSecLogSizeMin; SecLogSize -= 3)
+ Byte kSizesLog[] = { 11, 8, 12 };
+
+ for (int i = 0;; i++)
{
+ if (i == sizeof(kSizesLog) / sizeof(kSizesLog[0]))
+ return S_FALSE;
+ SecLogSize = kSizesLog[i];
Int32 bufSize = 1 << SecLogSize;
if (bufSize > fileSize)
return S_FALSE;
@@ -595,8 +597,8 @@ HRESULT CInArchive::Open2()
if (tag.Id == DESC_TYPE_AnchorVolPtr)
break;
}
- if (SecLogSize < kSecLogSizeMin)
- return S_FALSE;
+ if (SecLogSize == 12)
+ SecLogSize = 11;
CExtent extentVDS;
extentVDS.Parse(buf + 16);
diff --git a/CPP/7zip/Archive/VhdHandler.cpp b/CPP/7zip/Archive/VhdHandler.cpp
new file mode 100755
index 00000000..5fc2c918
--- /dev/null
+++ b/CPP/7zip/Archive/VhdHandler.cpp
@@ -0,0 +1,731 @@
+// VhdHandler.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/CpuArch.h"
+
+#include "Common/Buffer.h"
+#include "Common/ComTry.h"
+#include "Common/IntToString.h"
+#include "Common/MyString.h"
+
+#include "Windows/PropVariant.h"
+
+#include "../Common/LimitedStreams.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#define Get16(p) GetBe16(p)
+#define Get32(p) GetBe32(p)
+#define Get64(p) GetBe64(p)
+
+#define G32(p, dest) dest = Get32(p);
+#define G64(p, dest) dest = Get64(p);
+
+using namespace NWindows;
+
+namespace NArchive {
+namespace NVhd {
+
+static const UInt32 kUnusedBlock = 0xFFFFFFFF;
+
+static const UInt32 kDiskType_Fixed = 2;
+static const UInt32 kDiskType_Dynamic = 3;
+static const UInt32 kDiskType_Diff = 4;
+
+static const char *kDiskTypes[] =
+{
+ "0",
+ "1",
+ "Fixed",
+ "Dynamic",
+ "Differencing"
+};
+
+struct CFooter
+{
+ // UInt32 Features;
+ // UInt32 FormatVersion;
+ UInt64 DataOffset;
+ UInt32 CTime;
+ UInt32 CreatorApp;
+ UInt32 CreatorVersion;
+ UInt32 CreatorHostOS;
+ // UInt64 OriginalSize;
+ UInt64 CurrentSize;
+ UInt32 DiskGeometry;
+ UInt32 Type;
+ Byte Id[16];
+ Byte SavedState;
+
+ bool IsFixed() const { return Type == kDiskType_Fixed; }
+ bool ThereIsDynamic() const { return Type == kDiskType_Dynamic || Type == kDiskType_Diff; }
+ // bool IsSupported() const { return Type == kDiskType_Fixed || Type == kDiskType_Dynamic || Type == kDiskType_Diff; }
+ UInt32 NumCyls() const { return DiskGeometry >> 16; }
+ UInt32 NumHeads() const { return (DiskGeometry >> 8) & 0xFF; }
+ UInt32 NumSectorsPerTrack() const { return DiskGeometry & 0xFF; }
+ AString GetTypeString() const;
+ bool Parse(const Byte *p);
+};
+
+AString CFooter::GetTypeString() const
+{
+ if (Type < sizeof(kDiskTypes) / sizeof(kDiskTypes[0]))
+ return kDiskTypes[Type];
+ char s[16];
+ ConvertUInt32ToString(Type, s);
+ return s;
+}
+
+static bool CheckBlock(const Byte *p, unsigned size, unsigned checkSumOffset, unsigned zeroOffset)
+{
+ UInt32 sum = 0;
+ unsigned i;
+ for (i = 0; i < checkSumOffset; i++)
+ sum += p[i];
+ for (i = checkSumOffset + 4; i < size; i++)
+ sum += p[i];
+ if (~sum != Get32(p + checkSumOffset))
+ return false;
+ for (i = zeroOffset; i < size; i++)
+ if (p[i] != 0)
+ return false;
+ return true;
+}
+
+bool CFooter::Parse(const Byte *p)
+{
+ if (memcmp(p, "conectix", 8) != 0)
+ return false;
+ // G32(p + 0x08, Features);
+ // G32(p + 0x0C, FormatVersion);
+ G64(p + 0x10, DataOffset);
+ G32(p + 0x18, CTime);
+ G32(p + 0x1C, CreatorApp);
+ G32(p + 0x20, CreatorVersion);
+ G32(p + 0x24, CreatorHostOS);
+ // G64(p + 0x28, OriginalSize);
+ G64(p + 0x30, CurrentSize);
+ G32(p + 0x38, DiskGeometry);
+ G32(p + 0x3C, Type);
+ memcpy(Id, p + 0x44, 16);
+ SavedState = p[0x54];
+ return CheckBlock(p, 512, 0x40, 0x55);
+}
+
+/*
+struct CParentLocatorEntry
+{
+ UInt32 Code;
+ UInt32 DataSpace;
+ UInt32 DataLen;
+ UInt64 DataOffset;
+
+ bool Parse(const Byte *p);
+};
+bool CParentLocatorEntry::Parse(const Byte *p)
+{
+ G32(p + 0x00, Code);
+ G32(p + 0x04, DataSpace);
+ G32(p + 0x08, DataLen);
+ G32(p + 0x10, DataOffset);
+ return (Get32(p + 0x0C) == 0); // Resrved
+}
+*/
+
+struct CDynHeader
+{
+ // UInt64 DataOffset;
+ UInt64 TableOffset;
+ // UInt32 HeaderVersion;
+ UInt32 NumBlocks;
+ int BlockSizeLog;
+ UInt32 ParentTime;
+ Byte ParentId[16];
+ UString ParentName;
+ // CParentLocatorEntry ParentLocators[8];
+
+ bool Parse(const Byte *p);
+ UInt32 NumBitMapSectors() const
+ {
+ UInt32 numSectorsInBlock = (1 << (BlockSizeLog - 9));
+ return (numSectorsInBlock + 512 * 8 - 1) / (512 * 8);
+ }
+};
+
+static int GetLog(UInt32 num)
+{
+ for (int i = 0; i < 31; i++)
+ if (((UInt32)1 << i) == num)
+ return i;
+ return -1;
+}
+
+bool CDynHeader::Parse(const Byte *p)
+{
+ if (memcmp(p, "cxsparse", 8) != 0)
+ return false;
+ // G64(p + 0x08, DataOffset);
+ G64(p + 0x10, TableOffset);
+ // G32(p + 0x18, HeaderVersion);
+ G32(p + 0x1C, NumBlocks);
+ BlockSizeLog = GetLog(Get32(p + 0x20));
+ if (BlockSizeLog < 9 || BlockSizeLog > 30)
+ return false;
+ G32(p + 0x38, ParentTime);
+ if (Get32(p + 0x3C) != 0) // reserved
+ return false;
+ memcpy(ParentId, p + 0x28, 16);
+ {
+ const int kNameLength = 256;
+ wchar_t *s = ParentName.GetBuffer(kNameLength);
+ for (unsigned i = 0; i < kNameLength; i++)
+ s[i] = Get16(p + 0x40 + i * 2);
+ s[kNameLength] = 0;
+ ParentName.ReleaseBuffer();
+ }
+ /*
+ for (int i = 0; i < 8; i++)
+ if (!ParentLocators[i].Parse(p + 0x240 + i * 24))
+ return false;
+ */
+ return CheckBlock(p, 1024, 0x24, 0x240 + 8 * 24);
+}
+
+class CHandler:
+ public IInStream,
+ public IInArchive,
+ public IInArchiveGetStream,
+ public CMyUnknownImp
+{
+ UInt64 _virtPos;
+ UInt64 _phyPos;
+ UInt64 _phyLimit;
+
+ CFooter Footer;
+ CDynHeader Dyn;
+ CRecordVector<UInt32> Bat;
+ CByteBuffer BitMap;
+ UInt32 BitMapTag;
+ UInt32 NumUsedBlocks;
+ CMyComPtr<IInStream> Stream;
+ CMyComPtr<IInStream> ParentStream;
+ CHandler *Parent;
+
+ HRESULT Seek(UInt64 offset);
+ HRESULT InitAndSeek();
+ HRESULT ReadPhy(UInt64 offset, void *data, UInt32 size);
+
+ bool NeedParent() const { return Footer.Type == kDiskType_Diff; }
+ UInt64 GetSize() const { return Footer.CurrentSize; }
+ UInt64 GetPackSize() const
+ { return Footer.ThereIsDynamic() ? ((UInt64)NumUsedBlocks << Dyn.BlockSizeLog) : Footer.CurrentSize; }
+
+ UString GetParentName() const
+ {
+ const CHandler *p = this;
+ UString res;
+ while (p && p->NeedParent())
+ {
+ if (!res.IsEmpty())
+ res += L" -> ";
+ res += p->Dyn.ParentName;
+ p = p->Parent;
+ }
+ return res;
+ }
+
+ bool IsOK() const
+ {
+ const CHandler *p = this;
+ while (p->NeedParent())
+ {
+ p = p->Parent;
+ if (p == 0)
+ return false;
+ }
+ return true;
+ }
+
+ HRESULT Open3();
+ HRESULT Open2(IInStream *stream, CHandler *child, IArchiveOpenCallback *openArchiveCallback, int level);
+
+public:
+ MY_UNKNOWN_IMP3(IInArchive, IInArchiveGetStream, IInStream)
+
+ INTERFACE_IInArchive(;)
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+HRESULT CHandler::Seek(UInt64 offset) { return Stream->Seek(offset, STREAM_SEEK_SET, NULL); }
+
+HRESULT CHandler::InitAndSeek()
+{
+ if (ParentStream)
+ {
+ RINOK(Parent->InitAndSeek());
+ }
+ _virtPos = _phyPos = 0;
+ BitMapTag = kUnusedBlock;
+ BitMap.SetCapacity(Dyn.NumBitMapSectors() << 9);
+ return Seek(0);
+}
+
+HRESULT CHandler::ReadPhy(UInt64 offset, void *data, UInt32 size)
+{
+ if (offset + size > _phyLimit)
+ return S_FALSE;
+ if (offset != _phyPos)
+ {
+ _phyPos = offset;
+ RINOK(Seek(offset));
+ }
+ HRESULT res = ReadStream_FALSE(Stream, data, size);
+ _phyPos += size;
+ return res;
+}
+
+HRESULT CHandler::Open3()
+{
+ RINOK(Stream->Seek(0, STREAM_SEEK_END, &_phyPos));
+ if (_phyPos < 512)
+ return S_FALSE;
+ const UInt32 kDynSize = 1024;
+ Byte buf[kDynSize];
+
+ _phyLimit = _phyPos;
+ RINOK(ReadPhy(_phyLimit - 512, buf, 512));
+ if (!Footer.Parse(buf))
+ return S_FALSE;
+ _phyLimit -= 512;
+
+ if (!Footer.ThereIsDynamic())
+ return S_OK;
+
+ RINOK(ReadPhy(0, buf + 512, 512));
+ if (memcmp(buf, buf + 512, 512) != 0)
+ return S_FALSE;
+
+ RINOK(ReadPhy(Footer.DataOffset, buf, kDynSize));
+ if (!Dyn.Parse(buf))
+ return S_FALSE;
+
+ if (Dyn.NumBlocks >= (UInt32)1 << 31)
+ return S_FALSE;
+ if (GetSize() != ((UInt64)Dyn.NumBlocks << Dyn.BlockSizeLog))
+ return S_FALSE;
+
+ Bat.Reserve(Dyn.NumBlocks);
+ while ((UInt32)Bat.Size() < Dyn.NumBlocks)
+ {
+ RINOK(ReadPhy(Dyn.TableOffset + (UInt64)Bat.Size() * 4, buf, 512));
+ for (UInt32 j = 0; j < 512; j += 4)
+ {
+ UInt32 v = Get32(buf + j);
+ if (v != kUnusedBlock)
+ NumUsedBlocks++;
+ Bat.Add(v);
+ if ((UInt32)Bat.Size() >= Dyn.NumBlocks)
+ break;
+ }
+ }
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_virtPos >= GetSize())
+ return (GetSize() == _virtPos) ? S_OK: E_FAIL;
+ if (size == 0)
+ return S_OK;
+ UInt32 blockIndex = (UInt32)(_virtPos >> Dyn.BlockSizeLog);
+ UInt32 blockSectIndex = Bat[blockIndex];
+ UInt32 blockSize = (UInt32)1 << Dyn.BlockSizeLog;
+ UInt32 offsetInBlock = (UInt32)_virtPos & (blockSize - 1);
+ size = MyMin(blockSize - offsetInBlock, size);
+
+ HRESULT res = S_OK;
+ if (blockSectIndex == kUnusedBlock)
+ {
+ if (ParentStream)
+ {
+ RINOK(ParentStream->Seek(_virtPos, STREAM_SEEK_SET, NULL));
+ res = ParentStream->Read(data, size, &size);
+ }
+ else
+ memset(data, 0, size);
+ }
+ else
+ {
+ UInt64 newPos = (UInt64)blockSectIndex << 9;
+ if (BitMapTag != blockIndex)
+ {
+ RINOK(ReadPhy(newPos, BitMap, (UInt32)BitMap.GetCapacity()));
+ BitMapTag = blockIndex;
+ }
+ RINOK(ReadPhy(newPos + BitMap.GetCapacity() + offsetInBlock, data, size));
+ for (UInt32 cur = 0; cur < size;)
+ {
+ UInt32 rem = MyMin(0x200 - (offsetInBlock & 0x1FF), size - cur);
+ UInt32 bmi = offsetInBlock >> 9;
+ if (((BitMap[bmi >> 3] >> (7 - (bmi & 7))) & 1) == 0)
+ {
+ if (ParentStream)
+ {
+ RINOK(ParentStream->Seek(_virtPos + cur, STREAM_SEEK_SET, NULL));
+ RINOK(ReadStream_FALSE(ParentStream, (Byte *)data + cur, rem));
+ }
+ else
+ {
+ const Byte *p = (const Byte *)data + cur;
+ for (UInt32 i = 0; i < rem; i++)
+ if (p[i] != 0)
+ return S_FALSE;
+ }
+ }
+ offsetInBlock += rem;
+ cur += rem;
+ }
+ }
+ if (processedSize != NULL)
+ *processedSize = size;
+ _virtPos += size;
+ return res;
+}
+
+STDMETHODIMP CHandler::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: _virtPos = offset; break;
+ case STREAM_SEEK_CUR: _virtPos += offset; break;
+ case STREAM_SEEK_END: _virtPos = GetSize() + offset; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (newPosition)
+ *newPosition = _virtPos;
+ return S_OK;
+}
+
+enum
+{
+ kpidParent = kpidUserDefined,
+ kpidSavedState
+};
+
+STATPROPSTG kArcProps[] =
+{
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidCTime, VT_FILETIME},
+ { NULL, kpidClusterSize, VT_UI8},
+ { NULL, kpidMethod, VT_BSTR},
+ { L"Parent", kpidParent, VT_BSTR},
+ { NULL, kpidCreatorApp, VT_BSTR},
+ { NULL, kpidHostOS, VT_BSTR},
+ { L"Saved State", kpidSavedState, VT_BOOL},
+ { NULL, kpidId, VT_BSTR}
+ };
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidCTime, VT_FILETIME}
+
+ /*
+ { NULL, kpidNumCyls, VT_UI4},
+ { NULL, kpidNumHeads, VT_UI4},
+ { NULL, kpidSectorsPerTrack, VT_UI4}
+ */
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps_WITH_NAME
+
+// VHD start time: 2000-01-01
+static const UInt64 kVhdTimeStartValue = (UInt64)3600 * 24 * (399 * 365 + 24 * 4);
+
+static void VhdTimeToFileTime(UInt32 vhdTime, NCOM::CPropVariant &prop)
+{
+ FILETIME ft, utc;
+ UInt64 v = (kVhdTimeStartValue + vhdTime) * 10000000;
+ ft.dwLowDateTime = (DWORD)v;
+ ft.dwHighDateTime = (DWORD)(v >> 32);
+ // specification says that it's UTC time, but Virtual PC 6 writes local time. Why?
+ LocalFileTimeToFileTime(&ft, &utc);
+ prop = utc;
+}
+
+static void StringToAString(char *dest, UInt32 s)
+{
+ for (int i = 24; i >= 0; i -= 8)
+ {
+ Byte b = (Byte)((s >> i) & 0xFF);
+ if (b < 0x20 || b > 0x7F)
+ break;
+ *dest++ = b;
+ }
+ *dest = 0;
+}
+
+static void ConvertByteToHex(unsigned value, char *s)
+{
+ for (int i = 0; i < 2; i++)
+ {
+ unsigned t = value & 0xF;
+ value >>= 4;
+ s[1 - i] = (char)((t < 10) ? ('0' + t) : ('A' + (t - 10)));
+ }
+}
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidMainSubfile: prop = (UInt32)0; break;
+ case kpidCTime: VhdTimeToFileTime(Footer.CTime, prop); break;
+ case kpidClusterSize: if (Footer.ThereIsDynamic()) prop = (UInt32)1 << Dyn.BlockSizeLog; break;
+ case kpidMethod:
+ {
+ AString s = Footer.GetTypeString();
+ if (NeedParent())
+ {
+ s += " -> ";
+ const CHandler *p = this;
+ while (p != 0 && p->NeedParent())
+ p = p->Parent;
+ if (p == 0)
+ s += '?';
+ else
+ s += p->Footer.GetTypeString();
+ }
+ prop = s;
+ break;
+ }
+ case kpidCreatorApp:
+ {
+ char s[16];
+ StringToAString(s, Footer.CreatorApp);
+ AString res = s;
+ res.Trim();
+ ConvertUInt32ToString(Footer.CreatorVersion >> 16, s);
+ res += ' ';
+ res += s;
+ res += '.';
+ ConvertUInt32ToString(Footer.CreatorVersion & 0xFFFF, s);
+ res += s;
+ prop = res;
+ break;
+ }
+ case kpidHostOS:
+ {
+ if (Footer.CreatorHostOS == 0x5769326b)
+ prop = "Windows";
+ else
+ {
+ char s[16];
+ StringToAString(s, Footer.CreatorHostOS);
+ prop = s;
+ }
+ break;
+ }
+ case kpidId:
+ {
+ char s[32 + 4];
+ for (int i = 0; i < 16; i++)
+ ConvertByteToHex(Footer.Id[i], s + i * 2);
+ s[32] = 0;
+ prop = s;
+ break;
+ }
+ case kpidSavedState: prop = Footer.SavedState ? true : false; break;
+ case kpidParent: if (NeedParent()) prop = GetParentName(); break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+HRESULT CHandler::Open2(IInStream *stream, CHandler *child, IArchiveOpenCallback *openArchiveCallback, int level)
+{
+ Close();
+ Stream = stream;
+ if (level > 32)
+ return S_FALSE;
+ RINOK(Open3());
+ if (child && memcmp(child->Dyn.ParentId, Footer.Id, 16) != 0)
+ return S_FALSE;
+ if (Footer.Type != kDiskType_Diff)
+ return S_OK;
+ CMyComPtr<IArchiveOpenVolumeCallback> openVolumeCallback;
+ if (openArchiveCallback->QueryInterface(IID_IArchiveOpenVolumeCallback, (void **)&openVolumeCallback) != S_OK)
+ return S_FALSE;
+ CMyComPtr<IInStream> nextStream;
+ HRESULT res = openVolumeCallback->GetStream(Dyn.ParentName, &nextStream);
+ if (res == S_FALSE)
+ return S_OK;
+ RINOK(res);
+
+ Parent = new CHandler;
+ ParentStream = Parent;
+ return Parent->Open2(nextStream, this, openArchiveCallback, level + 1);
+}
+
+STDMETHODIMP CHandler::Open(IInStream *stream,
+ const UInt64 * /* maxCheckStartPosition */,
+ IArchiveOpenCallback * openArchiveCallback)
+{
+ COM_TRY_BEGIN
+ {
+ HRESULT res;
+ try
+ {
+ res = Open2(stream, NULL, openArchiveCallback, 0);
+ if (res == S_OK)
+ return S_OK;
+ }
+ catch(...)
+ {
+ Close();
+ throw;
+ }
+ Close();
+ return res;
+ }
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ Bat.Clear();
+ NumUsedBlocks = 0;
+ Parent = 0;
+ Stream.Release();
+ ParentStream.Release();
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = 1;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32 /* index */, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+
+ switch(propID)
+ {
+ case kpidSize: prop = GetSize(); break;
+ case kpidPackSize: prop = GetPackSize(); break;
+ case kpidCTime: VhdTimeToFileTime(Footer.CTime, prop); break;
+ /*
+ case kpidNumCyls: prop = Footer.NumCyls(); break;
+ case kpidNumHeads: prop = Footer.NumHeads(); break;
+ case kpidSectorsPerTrack: prop = Footer.NumSectorsPerTrack(); break;
+ */
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ if (numItems == UInt32(-1))
+ numItems = 1;
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
+
+ bool testMode = (_aTestMode != 0);
+
+ RINOK(extractCallback->SetTotal(GetSize()));
+ CMyComPtr<ISequentialOutStream> outStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+ RINOK(extractCallback->GetStream(0, &outStream, askMode));
+ if (!testMode && !outStream)
+ return S_OK;
+ RINOK(extractCallback->PrepareOperation(askMode));
+
+ NCompress::CCopyCoder *copyCoderSpec = new NCompress::CCopyCoder();
+ CMyComPtr<ICompressCoder> copyCoder = copyCoderSpec;
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, false);
+
+ int res = NArchive::NExtract::NOperationResult::kDataError;
+ CMyComPtr<ISequentialInStream> inStream;
+ HRESULT hres = GetStream(0, &inStream);
+ if (hres == S_FALSE)
+ res = NArchive::NExtract::NOperationResult::kUnSupportedMethod;
+ else
+ {
+ RINOK(hres);
+ HRESULT hres = copyCoder->Code(inStream, outStream, NULL, NULL, progress);
+ if (hres == S_OK)
+ {
+ if (copyCoderSpec->TotalSize == GetSize())
+ res = NArchive::NExtract::NOperationResult::kOK;
+ }
+ else
+ {
+ if (hres != S_FALSE)
+ {
+ RINOK(hres);
+ }
+ }
+ }
+ outStream.Release();
+ return extractCallback->SetOperationResult(res);
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetStream(UInt32 /* index */, ISequentialInStream **stream)
+{
+ COM_TRY_BEGIN
+ *stream = 0;
+ if (Footer.IsFixed())
+ {
+ CLimitedInStream *streamSpec = new CLimitedInStream;
+ CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
+ streamSpec->SetStream(Stream);
+ streamSpec->InitAndSeek(0, GetSize());
+ RINOK(streamSpec->SeekToStart());
+ *stream = streamTemp.Detach();
+ return S_OK;
+ }
+ if (!Footer.ThereIsDynamic() || !IsOK())
+ return S_FALSE;
+ CMyComPtr<ISequentialInStream> streamTemp = this;
+ RINOK(InitAndSeek());
+ *stream = streamTemp.Detach();
+ return S_OK;
+ COM_TRY_END
+}
+
+static IInArchive *CreateArc() { return new CHandler; }
+
+static CArcInfo g_ArcInfo =
+ { L"VHD", L"vhd", L".mbr", 0xDC, { 'c', 'o', 'n', 'e', 'c', 't', 'i', 'x', 0, 0 }, 10, false, CreateArc, 0 };
+
+REGISTER_ARC(Vhd)
+
+}}
diff --git a/CPP/7zip/Archive/Wim/WimIn.cpp b/CPP/7zip/Archive/Wim/WimIn.cpp
index 121e33ab..90c3c2c2 100755
--- a/CPP/7zip/Archive/Wim/WimIn.cpp
+++ b/CPP/7zip/Archive/Wim/WimIn.cpp
@@ -2,7 +2,8 @@
#include "StdAfx.h"
-#include "Common/MyCom.h"
+#include "../../../../C/CpuArch.h"
+
#include "Common/IntToString.h"
#include "../../Common/StreamUtils.h"
@@ -11,8 +12,6 @@
#include "../Common/OutStreamWithSha1.h"
-#include "../../../../C/CpuArch.h"
-
#include "WimIn.h"
#define Get16(p) GetUi16(p)
@@ -354,7 +353,7 @@ static HRESULT ParseDir(const Byte *base, size_t size,
sum += len;
pos += 8;
}
- pos += sum; // skeep security descriptors
+ pos += sum; // skip security descriptors
while ((pos & 7) != 0)
pos++;
if (pos != totalLength)
@@ -498,8 +497,8 @@ HRESULT OpenArchive(IInStream *inStream, const CHeader &h, CByteBuffer &xml, CDa
RINOK(UnpackData(inStream, si.Resource, h.IsLzxMode(), metadata, hash));
if (memcmp(hash, si.Hash, kHashSize) != 0)
return S_FALSE;
- wchar_t sz[32];
- ConvertUInt64ToString(imageIndex++, sz);
+ wchar_t sz[16];
+ ConvertUInt32ToString(imageIndex++, sz);
UString s = sz;
s += WCHAR_PATH_SEPARATOR;
RINOK(ParseDir(metadata, metadata.GetCapacity(), s, db.Items));
diff --git a/CPP/7zip/Archive/XzHandler.cpp b/CPP/7zip/Archive/XzHandler.cpp
new file mode 100755
index 00000000..116e96b6
--- /dev/null
+++ b/CPP/7zip/Archive/XzHandler.cpp
@@ -0,0 +1,714 @@
+// XzHandler.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/Alloc.h"
+#include "../../../C/XzCrc64.h"
+#include "../../../C/XzEnc.h"
+
+#include "../../Common/ComTry.h"
+#include "../../Common/IntToString.h"
+
+#include "../ICoder.h"
+
+#include "../Common/CWrappers.h"
+#include "../Common/ProgressUtils.h"
+#include "../Common/RegisterArc.h"
+#include "../Common/StreamUtils.h"
+
+#include "../Compress/CopyCoder.h"
+
+#include "IArchive.h"
+
+#include "Common/HandlerOut.h"
+
+using namespace NWindows;
+
+namespace NCompress {
+namespace NLzma2 {
+
+HRESULT SetLzma2Prop(PROPID propID, const PROPVARIANT &prop, CLzma2EncProps &lzma2Props);
+
+}}
+
+static void *SzAlloc(void *, size_t size) { return MyAlloc(size); }
+static void SzFree(void *, void *address) { MyFree(address); }
+static ISzAlloc g_Alloc = { SzAlloc, SzFree };
+
+namespace NArchive {
+namespace NXz {
+
+struct CCrc64Gen { CCrc64Gen() { Crc64GenerateTable(); } } g_Crc64TableInit;
+
+class CHandler:
+ public IInArchive,
+ public IArchiveOpenSeq,
+ #ifndef EXTRACT_ONLY
+ public IOutArchive,
+ public ISetProperties,
+ public COutHandler,
+ #endif
+ public CMyUnknownImp
+{
+ Int64 _startPosition;
+ UInt64 _packSize;
+ UInt64 _unpackSize;
+ UInt64 _numBlocks;
+ AString _methodsString;
+ bool _useSeq;
+ UInt64 _unpackSizeDefined;
+ UInt64 _packSizeDefined;
+
+ CMyComPtr<IInStream> _stream;
+ CMyComPtr<ISequentialInStream> _seqStream;
+
+ UInt32 _crcSize;
+
+ void Init()
+ {
+ _crcSize = 4;
+ COutHandler::Init();
+ }
+
+ HRESULT Open2(IInStream *inStream, IArchiveOpenCallback *callback);
+
+public:
+ MY_QUERYINTERFACE_BEGIN
+ MY_QUERYINTERFACE_ENTRY(IInArchive)
+ MY_QUERYINTERFACE_ENTRY(IArchiveOpenSeq)
+ #ifndef EXTRACT_ONLY
+ MY_QUERYINTERFACE_ENTRY(IOutArchive)
+ MY_QUERYINTERFACE_ENTRY(ISetProperties)
+ #endif
+ MY_QUERYINTERFACE_END
+ MY_ADDREF_RELEASE
+
+ INTERFACE_IInArchive(;)
+ STDMETHOD(OpenSeq)(ISequentialInStream *stream);
+
+ #ifndef EXTRACT_ONLY
+ INTERFACE_IOutArchive(;)
+ STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProps);
+ #endif
+
+ CHandler();
+};
+
+CHandler::CHandler()
+{
+ Init();
+}
+
+STATPROPSTG kProps[] =
+{
+ { NULL, kpidSize, VT_UI8},
+ { NULL, kpidPackSize, VT_UI8},
+ { NULL, kpidMethod, VT_BSTR}
+};
+
+STATPROPSTG kArcProps[] =
+{
+ { NULL, kpidMethod, VT_BSTR},
+ { NULL, kpidNumBlocks, VT_UI4}
+};
+
+IMP_IInArchive_Props
+IMP_IInArchive_ArcProps
+
+static char GetHex(Byte value)
+{
+ return (char)((value < 10) ? ('0' + value) : ('A' + (value - 10)));
+}
+
+static inline void AddHexToString(AString &res, Byte value)
+{
+ res += GetHex((Byte)(value >> 4));
+ res += GetHex((Byte)(value & 0xF));
+}
+
+static AString ConvertUInt32ToString(UInt32 value)
+{
+ char temp[32];
+ ::ConvertUInt32ToString(value, temp);
+ return temp;
+}
+
+static AString Lzma2PropToString(int prop)
+{
+ if ((prop & 1) == 0)
+ return ConvertUInt32ToString(prop / 2 + 12);
+ AString res;
+ char c;
+
+ UInt32 size = (2 | ((prop) & 1)) << ((prop) / 2 + 1);
+
+ if (prop > 17)
+ {
+ res = ConvertUInt32ToString(size >> 10);
+ c = 'm';
+ }
+ else
+ {
+ res = ConvertUInt32ToString(size);
+ c = 'k';
+ }
+ return res + c;
+}
+
+struct CMethodNamePair
+{
+ UInt32 Id;
+ const char *Name;
+};
+
+static CMethodNamePair g_NamePairs[] =
+{
+ { XZ_ID_Subblock, "SB" },
+ { XZ_ID_Delta, "Delta" },
+ { XZ_ID_X86, "x86" },
+ { XZ_ID_PPC, "PPC" },
+ { XZ_ID_IA64, "IA64" },
+ { XZ_ID_ARM, "ARM" },
+ { XZ_ID_ARMT, "ARMT" },
+ { XZ_ID_SPARC, "SPARC" },
+ { XZ_ID_LZMA2, "LZMA2" }
+};
+
+static AString GetMethodString(const CXzFilter &f)
+{
+ AString s;
+
+ for (int i = 0; i < sizeof(g_NamePairs) / sizeof(g_NamePairs[i]); i++)
+ if (g_NamePairs[i].Id == f.id)
+ s = g_NamePairs[i].Name;
+ if (s.IsEmpty())
+ {
+ char temp[32];
+ ::ConvertUInt64ToString(f.id, temp);
+ s = temp;
+ }
+
+ if (f.propsSize > 0)
+ {
+ s += ':';
+ if (f.id == XZ_ID_LZMA2 && f.propsSize == 1)
+ s += Lzma2PropToString(f.props[0]);
+ else if (f.id == XZ_ID_Delta && f.propsSize == 1)
+ s += ConvertUInt32ToString((UInt32)f.props[0] + 1);
+ else
+ {
+ s += '[';
+ for (UInt32 bi = 0; bi < f.propsSize; bi++)
+ AddHexToString(s, f.props[bi]);
+ s += ']';
+ }
+ }
+ return s;
+}
+
+static void AddString(AString &dest, const AString &src)
+{
+ if (!dest.IsEmpty())
+ dest += ' ';
+ dest += src;
+}
+
+static const char *kChecks[] =
+{
+ "NoCheck",
+ "CRC32",
+ NULL,
+ NULL,
+ "CRC64",
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ "SHA256",
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL
+};
+
+static AString GetCheckString(const CXzs &xzs)
+{
+ size_t i;
+ UInt32 mask = 0;
+ for (i = 0; i < xzs.num; i++)
+ mask |= ((UInt32)1 << XzFlags_GetCheckType(xzs.streams[i].flags));
+ AString s;
+ for (i = 0; i <= XZ_CHECK_MASK; i++)
+ if (((mask >> i) & 1) != 0)
+ {
+ AString s2;
+ if (kChecks[i])
+ s2 = kChecks[i];
+ else
+ s2 = "Check-" + ConvertUInt32ToString((UInt32)i);
+ AddString(s, s2);
+ }
+ return s;
+}
+
+STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidNumBlocks: if (!_useSeq) prop = _numBlocks; break;
+ case kpidPhySize: if (_packSizeDefined) prop = _packSize; break;
+ case kpidMethod: if (!_methodsString.IsEmpty()) prop = _methodsString; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems)
+{
+ *numItems = 1;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::GetProperty(UInt32, PROPID propID, PROPVARIANT *value)
+{
+ COM_TRY_BEGIN
+ NWindows::NCOM::CPropVariant prop;
+ switch(propID)
+ {
+ case kpidSize: if (_unpackSizeDefined) prop = _unpackSize; break;
+ case kpidPackSize: if (_packSizeDefined) prop = _packSize; break;
+ case kpidMethod: if (!_methodsString.IsEmpty()) prop = _methodsString; break;
+ }
+ prop.Detach(value);
+ return S_OK;
+ COM_TRY_END
+}
+
+
+struct COpenCallbackWrap
+{
+ ICompressProgress p;
+ IArchiveOpenCallback *OpenCallback;
+ HRESULT Res;
+ COpenCallbackWrap(IArchiveOpenCallback *progress);
+};
+
+static SRes OpenCallbackProgress(void *pp, UInt64 inSize, UInt64 /* outSize */)
+{
+ COpenCallbackWrap *p = (COpenCallbackWrap *)pp;
+ p->Res = p->OpenCallback->SetCompleted(NULL, &inSize);
+ return (SRes)p->Res;
+}
+
+COpenCallbackWrap::COpenCallbackWrap(IArchiveOpenCallback *callback)
+{
+ p.Progress = OpenCallbackProgress;
+ OpenCallback = callback;
+ Res = SZ_OK;
+}
+
+struct CXzsCPP
+{
+ CXzs p;
+ CXzsCPP() { Xzs_Construct(&p); }
+ ~CXzsCPP() { Xzs_Free(&p, &g_Alloc); }
+};
+
+HRESULT CHandler::Open2(IInStream *inStream, IArchiveOpenCallback *callback)
+{
+ CSeekInStreamWrap inStreamImp(inStream);
+
+ CLookToRead lookStream;
+ LookToRead_CreateVTable(&lookStream, True);
+ lookStream.realStream = &inStreamImp.p;
+ LookToRead_Init(&lookStream);
+
+ COpenCallbackWrap openWrap(callback);
+ RINOK(inStream->Seek(0, STREAM_SEEK_END, &_packSize));
+ RINOK(callback->SetTotal(NULL, &_packSize));
+
+ CXzsCPP xzs;
+ SRes res = Xzs_ReadBackward(&xzs.p, &lookStream.s, &_startPosition, &openWrap.p, &g_Alloc);
+ if (res == SZ_ERROR_NO_ARCHIVE && xzs.p.num > 0)
+ res = SZ_OK;
+ if (res == SZ_OK)
+ {
+ _packSize -= _startPosition;
+ _unpackSize = Xzs_GetUnpackSize(&xzs.p);
+ _unpackSizeDefined = _packSizeDefined = true;
+ _numBlocks = (UInt64)Xzs_GetNumBlocks(&xzs.p);
+
+ RINOK(inStream->Seek(0, STREAM_SEEK_SET, NULL));
+ CXzStreamFlags st;
+ CSeqInStreamWrap inStreamWrap(inStream);
+ SRes res2 = Xz_ReadHeader(&st, &inStreamWrap.p);
+
+ if (res2 == SZ_OK)
+ {
+ CXzBlock block;
+ Bool isIndex;
+ UInt32 headerSizeRes;
+ res2 = XzBlock_ReadHeader(&block, &inStreamWrap.p, &isIndex, &headerSizeRes);
+ if (res2 == SZ_OK && !isIndex)
+ {
+ int numFilters = XzBlock_GetNumFilters(&block);
+ for (int i = 0; i < numFilters; i++)
+ AddString(_methodsString, GetMethodString(block.filters[i]));
+ }
+ }
+ AddString(_methodsString, GetCheckString(xzs.p));
+ }
+
+ if (res != SZ_OK || _startPosition != 0)
+ {
+ RINOK(inStream->Seek(0, STREAM_SEEK_SET, NULL));
+ CXzStreamFlags st;
+ CSeqInStreamWrap inStreamWrap(inStream);
+ SRes res2 = Xz_ReadHeader(&st, &inStreamWrap.p);
+ if (res2 == SZ_OK)
+ {
+ res = res2;
+ _startPosition = 0;
+ _useSeq = True;
+ _unpackSizeDefined = _packSizeDefined = false;
+ }
+ }
+ if (res == SZ_ERROR_NO_ARCHIVE)
+ return S_FALSE;
+ RINOK(SResToHRESULT(res));
+ _stream = inStream;
+ _seqStream = inStream;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Open(IInStream *inStream, const UInt64 *, IArchiveOpenCallback *callback)
+{
+ COM_TRY_BEGIN
+ try
+ {
+ Close();
+ return Open2(inStream, callback);
+ }
+ catch(...) { return S_FALSE; }
+ COM_TRY_END
+}
+
+STDMETHODIMP CHandler::OpenSeq(ISequentialInStream *stream)
+{
+ Close();
+ _seqStream = stream;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::Close()
+{
+ _numBlocks = 0;
+ _useSeq = true;
+ _unpackSizeDefined = _packSizeDefined = false;
+ _methodsString.Empty();
+ _stream.Release();
+ _seqStream.Release();
+ return S_OK;
+}
+
+class CSeekToSeqStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+public:
+ CMyComPtr<ISequentialInStream> Stream;
+ MY_UNKNOWN_IMP1(IInStream)
+
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+STDMETHODIMP CSeekToSeqStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ return Stream->Read(data, size, processedSize);
+}
+
+STDMETHODIMP CSeekToSeqStream::Seek(Int64, UInt32, UInt64 *) { return E_NOTIMPL; }
+
+struct CXzUnpackerCPP
+{
+ Byte *InBuf;
+ Byte *OutBuf;
+ CXzUnpacker p;
+ CXzUnpackerCPP(): InBuf(0), OutBuf(0) {}
+ ~CXzUnpackerCPP()
+ {
+ XzUnpacker_Free(&p);
+ MyFree(InBuf);
+ MyFree(OutBuf);
+ }
+};
+
+STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
+ Int32 _aTestMode, IArchiveExtractCallback *extractCallback)
+{
+ COM_TRY_BEGIN
+ bool allFilesMode = (numItems == UInt32(-1));
+ if (!allFilesMode)
+ {
+ if (numItems == 0)
+ return S_OK;
+ if (numItems != 1 || indices[0] != 0)
+ return E_INVALIDARG;
+ }
+
+ bool testMode = (_aTestMode != 0);
+
+ extractCallback->SetTotal(_packSize);
+ UInt64 currentTotalPacked = 0;
+ RINOK(extractCallback->SetCompleted(&currentTotalPacked));
+ CMyComPtr<ISequentialOutStream> realOutStream;
+ Int32 askMode = testMode ?
+ NArchive::NExtract::NAskMode::kTest :
+ NArchive::NExtract::NAskMode::kExtract;
+
+ RINOK(extractCallback->GetStream(0, &realOutStream, askMode));
+
+ if (!testMode && !realOutStream)
+ return S_OK;
+
+ extractCallback->PrepareOperation(askMode);
+
+ if (_stream)
+ {
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ }
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(extractCallback, true);
+
+ CCompressProgressWrap progressWrap(progress);
+
+ SRes res;
+
+ const UInt32 kInBufSize = 1 << 15;
+ const UInt32 kOutBufSize = 1 << 21;
+
+ UInt32 inPos = 0;
+ UInt32 inSize = 0;
+ UInt32 outPos = 0;
+ CXzUnpackerCPP xzu;
+ res = XzUnpacker_Create(&xzu.p, &g_Alloc);
+ if (res == SZ_OK)
+ {
+ xzu.InBuf = (Byte *)MyAlloc(kInBufSize);
+ xzu.OutBuf = (Byte *)MyAlloc(kOutBufSize);
+ if (xzu.InBuf == 0 || xzu.OutBuf == 0)
+ res = SZ_ERROR_MEM;
+ }
+ if (res == SZ_OK)
+ for (;;)
+ {
+ if (inPos == inSize)
+ {
+ inPos = inSize = 0;
+ RINOK(_seqStream->Read(xzu.InBuf, kInBufSize, &inSize));
+ }
+
+ SizeT inLen = inSize - inPos;
+ SizeT outLen = kOutBufSize - outPos;
+ ECoderStatus status;
+ res = XzUnpacker_Code(&xzu.p,
+ xzu.OutBuf + outPos, &outLen,
+ xzu.InBuf + inPos, &inLen,
+ (inSize == 0 ? CODER_FINISH_END : CODER_FINISH_ANY), &status);
+
+ // printf("\n_inPos = %6d inLen = %5d, outLen = %5d", inPos, inLen, outLen);
+
+ inPos += (UInt32)inLen;
+ outPos += (UInt32)outLen;
+ lps->InSize += inLen;
+ lps->OutSize += outLen;
+
+ bool finished = (((inLen == 0) && (outLen == 0)) || res != SZ_OK);
+
+ if (outPos == kOutBufSize || finished)
+ {
+ if (realOutStream && outPos > 0)
+ {
+ RINOK(WriteStream(realOutStream, xzu.OutBuf, outPos));
+ }
+ outPos = 0;
+ }
+ if (finished)
+ {
+ _packSize = lps->InSize;
+ _unpackSize = lps->OutSize;
+ _packSizeDefined = _unpackSizeDefined = true;
+ if (res == SZ_OK)
+ {
+ if (status == CODER_STATUS_NEEDS_MORE_INPUT)
+ {
+ if (XzUnpacker_IsStreamWasFinished(&xzu.p))
+ _packSize -= xzu.p.padSize;
+ else
+ res = SZ_ERROR_DATA;
+ }
+ else
+ res = SZ_ERROR_DATA;
+ }
+ break;
+ }
+ RINOK(lps->SetCur());
+ }
+
+ Int32 opRes;
+ switch(res)
+ {
+ case SZ_OK:
+ opRes = NArchive::NExtract::NOperationResult::kOK; break;
+ case SZ_ERROR_UNSUPPORTED:
+ opRes = NArchive::NExtract::NOperationResult::kUnSupportedMethod; break;
+ case SZ_ERROR_CRC:
+ opRes = NArchive::NExtract::NOperationResult::kCRCError; break;
+ case SZ_ERROR_DATA:
+ case SZ_ERROR_ARCHIVE:
+ case SZ_ERROR_NO_ARCHIVE:
+ opRes = NArchive::NExtract::NOperationResult::kDataError; break;
+ default:
+ return SResToHRESULT(res);
+ }
+ realOutStream.Release();
+ RINOK(extractCallback->SetOperationResult(opRes));
+ return S_OK;
+ COM_TRY_END
+}
+
+#ifndef EXTRACT_ONLY
+
+STDMETHODIMP CHandler::GetFileTimeType(UInt32 *timeType)
+{
+ *timeType = NFileTimeType::kUnix;
+ return S_OK;
+}
+
+STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,
+ IArchiveUpdateCallback *updateCallback)
+{
+ CSeqOutStreamWrap seqOutStream(outStream);
+
+ if (numItems == 0)
+ {
+ SRes res = Xz_EncodeEmpty(&seqOutStream.p);
+ return SResToHRESULT(res);
+ }
+
+ if (numItems != 1)
+ return E_INVALIDARG;
+
+ Int32 newData, newProps;
+ UInt32 indexInArchive;
+ if (!updateCallback)
+ return E_FAIL;
+ RINOK(updateCallback->GetUpdateItemInfo(0, &newData, &newProps, &indexInArchive));
+
+ if (IntToBool(newProps))
+ {
+ {
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidIsDir, &prop));
+ if (prop.vt != VT_EMPTY)
+ if (prop.vt != VT_BOOL || prop.boolVal != VARIANT_FALSE)
+ return E_INVALIDARG;
+ }
+ }
+
+ if (IntToBool(newData))
+ {
+ {
+ UInt64 size;
+ NCOM::CPropVariant prop;
+ RINOK(updateCallback->GetProperty(0, kpidSize, &prop));
+ if (prop.vt != VT_UI8)
+ return E_INVALIDARG;
+ size = prop.uhVal.QuadPart;
+ RINOK(updateCallback->SetTotal(size));
+ }
+
+ CLzma2EncProps lzma2Props;
+ Lzma2EncProps_Init(&lzma2Props);
+
+ lzma2Props.lzmaProps.level = _level;
+
+ CMyComPtr<ISequentialInStream> fileInStream;
+ RINOK(updateCallback->GetStream(0, &fileInStream));
+
+ CSeqInStreamWrap seqInStream(fileInStream);
+
+ for (int i = 0; i < _methods.Size(); i++)
+ {
+ COneMethodInfo &m = _methods[i];
+ SetCompressionMethod2(m
+ #ifdef COMPRESS_MT
+ , _numThreads
+ #endif
+ );
+ if (m.IsLzma())
+ {
+ for (int j = 0; j < m.Props.Size(); j++)
+ {
+ const CProp &prop = m.Props[j];
+ RINOK(NCompress::NLzma2::SetLzma2Prop(prop.Id, prop.Value, lzma2Props));
+ }
+ }
+ }
+
+ #ifdef COMPRESS_MT
+ lzma2Props.numTotalThreads = _numThreads;
+ #endif
+
+ CLocalProgress *lps = new CLocalProgress;
+ CMyComPtr<ICompressProgressInfo> progress = lps;
+ lps->Init(updateCallback, true);
+
+ CCompressProgressWrap progressWrap(progress);
+ SRes res = Xz_Encode(&seqOutStream.p, &seqInStream.p, &lzma2Props, False, &progressWrap.p);
+ if (res == SZ_OK)
+ return updateCallback->SetOperationResult(NArchive::NUpdate::NOperationResult::kOK);
+ return SResToHRESULT(res);
+ }
+ if (indexInArchive != 0)
+ return E_INVALIDARG;
+ if (_stream)
+ RINOK(_stream->Seek(_startPosition, STREAM_SEEK_SET, NULL));
+ return NCompress::CopyStream(_stream, outStream, 0);
+}
+
+STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProps)
+{
+ COM_TRY_BEGIN
+ BeforeSetProperty();
+ for (int i = 0; i < numProps; i++)
+ {
+ RINOK(SetProperty(names[i], values[i]));
+ }
+ return S_OK;
+ COM_TRY_END
+}
+
+#endif
+
+static IInArchive *CreateArc() { return new NArchive::NXz::CHandler; }
+#ifndef EXTRACT_ONLY
+static IOutArchive *CreateArcOut() { return new NArchive::NXz::CHandler; }
+#else
+#define CreateArcOut 0
+#endif
+
+static CArcInfo g_ArcInfo =
+ { L"xz", L"xz txz", L"* .tar", 0xC, {0xFD, '7' , 'z', 'X', 'Z', '\0'}, 6, true, CreateArc, CreateArcOut };
+
+REGISTER_ARC(xz)
+
+}}
diff --git a/CPP/7zip/Archive/Zip/ZipAddCommon.cpp b/CPP/7zip/Archive/Zip/ZipAddCommon.cpp
index 212a8b4b..9157deeb 100755
--- a/CPP/7zip/Archive/Zip/ZipAddCommon.cpp
+++ b/CPP/7zip/Archive/Zip/ZipAddCommon.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../../C/7zCrc.h"
-}
#include "Windows/PropVariant.h"
diff --git a/CPP/7zip/Archive/Zip/ZipHandler.cpp b/CPP/7zip/Archive/Zip/ZipHandler.cpp
index 25cbd886..547ecf92 100755
--- a/CPP/7zip/Archive/Zip/ZipHandler.cpp
+++ b/CPP/7zip/Archive/Zip/ZipHandler.cpp
@@ -3,16 +3,13 @@
#include "StdAfx.h"
#include "Common/ComTry.h"
-#include "Common/Defs.h"
#include "Common/IntToString.h"
-#include "Common/StringConvert.h"
#include "Windows/PropVariant.h"
#include "Windows/Time.h"
#include "../../IPassword.h"
-#include "../../Common/CreateCoder.h"
#include "../../Common/FilterCoder.h"
#include "../../Common/ProgressUtils.h"
#include "../../Common/StreamObjects.h"
@@ -37,38 +34,34 @@ using namespace NWindows;
namespace NArchive {
namespace NZip {
-// static const CMethodId kMethodId_Store = 0;
static const CMethodId kMethodId_ZipBase = 0x040100;
static const CMethodId kMethodId_BZip2 = 0x040202;
-const wchar_t *kHostOS[] =
+static const char *kHostOS[] =
{
- L"FAT",
- L"AMIGA",
- L"VMS",
- L"Unix",
- L"VM/CMS",
- L"Atari",
- L"HPFS",
- L"Macintosh",
- L"Z-System",
- L"CP/M",
- L"TOPS-20",
- L"NTFS",
- L"SMS/QDOS",
- L"Acorn",
- L"VFAT",
- L"MVS",
- L"BeOS",
- L"Tandem",
- L"OS/400",
- L"OS/X"
+ "FAT",
+ "AMIGA",
+ "VMS",
+ "Unix",
+ "VM/CMS",
+ "Atari",
+ "HPFS",
+ "Macintosh",
+ "Z-System",
+ "CP/M",
+ "TOPS-20",
+ "NTFS",
+ "SMS/QDOS",
+ "Acorn",
+ "VFAT",
+ "MVS",
+ "BeOS",
+ "Tandem",
+ "OS/400",
+ "OS/X"
};
-
-static const int kNumHostOSes = sizeof(kHostOS) / sizeof(kHostOS[0]);
-
-static const wchar_t *kUnknownOS = L"Unknown";
+static const char *kUnknownOS = "Unknown";
STATPROPSTG kProps[] =
{
@@ -93,50 +86,50 @@ STATPROPSTG kProps[] =
// { NULL, kpidUnpackVer, VT_UI1},
};
-const wchar_t *kMethods[] =
+const char *kMethods[] =
{
- L"Store",
- L"Shrink",
- L"Reduced1",
- L"Reduced2",
- L"Reduced2",
- L"Reduced3",
- L"Implode",
- L"Tokenizing",
- L"Deflate",
- L"Deflate64",
- L"PKImploding"
+ "Store",
+ "Shrink",
+ "Reduced1",
+ "Reduced2",
+ "Reduced2",
+ "Reduced3",
+ "Implode",
+ "Tokenizing",
+ "Deflate",
+ "Deflate64",
+ "PKImploding"
};
const int kNumMethods = sizeof(kMethods) / sizeof(kMethods[0]);
-const wchar_t *kBZip2Method = L"BZip2";
-const wchar_t *kLZMAMethod = L"LZMA";
-const wchar_t *kJpegMethod = L"Jpeg";
-const wchar_t *kWavPackMethod = L"WavPack";
-const wchar_t *kPPMdMethod = L"PPMd";
-const wchar_t *kAESMethod = L"AES";
-const wchar_t *kZipCryptoMethod = L"ZipCrypto";
-const wchar_t *kStrongCryptoMethod = L"StrongCrypto";
+const char *kBZip2Method = "BZip2";
+const char *kLZMAMethod = "LZMA";
+const char *kJpegMethod = "Jpeg";
+const char *kWavPackMethod = "WavPack";
+const char *kPPMdMethod = "PPMd";
+const char *kAESMethod = "AES";
+const char *kZipCryptoMethod = "ZipCrypto";
+const char *kStrongCryptoMethod = "StrongCrypto";
struct CStrongCryptoPair
{
UInt16 Id;
- const wchar_t *Name;
+ const char *Name;
};
CStrongCryptoPair g_StrongCryptoPairs[] =
{
- { NStrongCryptoFlags::kDES, L"DES" },
- { NStrongCryptoFlags::kRC2old, L"RC2a" },
- { NStrongCryptoFlags::k3DES168, L"3DES-168" },
- { NStrongCryptoFlags::k3DES112, L"3DES-112" },
- { NStrongCryptoFlags::kAES128, L"pkAES-128" },
- { NStrongCryptoFlags::kAES192, L"pkAES-192" },
- { NStrongCryptoFlags::kAES256, L"pkAES-256" },
- { NStrongCryptoFlags::kRC2, L"RC2" },
- { NStrongCryptoFlags::kBlowfish, L"Blowfish" },
- { NStrongCryptoFlags::kTwofish, L"Twofish" },
- { NStrongCryptoFlags::kRC4, L"RC4" }
+ { NStrongCryptoFlags::kDES, "DES" },
+ { NStrongCryptoFlags::kRC2old, "RC2a" },
+ { NStrongCryptoFlags::k3DES168, "3DES-168" },
+ { NStrongCryptoFlags::k3DES112, "3DES-112" },
+ { NStrongCryptoFlags::kAES128, "pkAES-128" },
+ { NStrongCryptoFlags::kAES192, "pkAES-192" },
+ { NStrongCryptoFlags::kAES256, "pkAES-256" },
+ { NStrongCryptoFlags::kRC2, "RC2" },
+ { NStrongCryptoFlags::kBlowfish, "Blowfish" },
+ { NStrongCryptoFlags::kTwofish, "Twofish" },
+ { NStrongCryptoFlags::kRC4, "RC4" }
};
STATPROPSTG kArcProps[] =
@@ -202,9 +195,14 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidPackSize: prop = item.PackSize; break;
case kpidTimeType:
{
- FILETIME utcFileTime;
- if (item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kTagTime, utcFileTime))
+ FILETIME ft;
+ UInt32 unixTime;
+ if (item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, ft))
prop = (UInt32)NFileTimeType::kWindows;
+ else if (item.CentralExtra.GetUnixTime(NFileHeader::NUnixTime::kMTime, unixTime))
+ prop = (UInt32)NFileTimeType::kUnix;
+ else
+ prop = (UInt32)NFileTimeType::kDOS;
break;
}
case kpidCTime:
@@ -223,19 +221,21 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
}
case kpidMTime:
{
- FILETIME utcFileTime;
- if (!item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, utcFileTime))
+ FILETIME utc;
+ if (!item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, utc))
{
- FILETIME localFileTime;
- if (NTime::DosTimeToFileTime(item.Time, localFileTime))
+ UInt32 unixTime;
+ if (item.CentralExtra.GetUnixTime(NFileHeader::NUnixTime::kMTime, unixTime))
+ NTime::UnixTimeToFileTime(unixTime, utc);
+ else
{
- if (!LocalFileTimeToFileTime(&localFileTime, &utcFileTime))
- utcFileTime.dwHighDateTime = utcFileTime.dwLowDateTime = 0;
+ FILETIME localFileTime;
+ if (!NTime::DosTimeToFileTime(item.Time, localFileTime) ||
+ !LocalFileTimeToFileTime(&localFileTime, &utc))
+ utc.dwHighDateTime = utc.dwLowDateTime = 0;
}
- else
- utcFileTime.dwHighDateTime = utcFileTime.dwLowDateTime = 0;
}
- prop = utcFileTime;
+ prop = utc;
break;
}
case kpidAttrib: prop = item.GetWinAttributes(); break;
@@ -245,7 +245,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidMethod:
{
UInt16 methodId = item.CompressionMethod;
- UString method;
+ AString method;
if (item.IsEncrypted())
{
if (methodId == NFileHeader::NCompressionMethod::kWzAES)
@@ -254,11 +254,11 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
CWzAesExtraField aesField;
if (item.CentralExtra.GetWzAesField(aesField))
{
- method += L"-";
- wchar_t s[32];
+ method += '-';
+ char s[32];
ConvertUInt64ToString((aesField.Strength + 1) * 64 , s);
method += s;
- method += L" ";
+ method += ' ';
methodId = aesField.Method;
}
}
@@ -286,7 +286,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
}
else
method += kZipCryptoMethod;
- method += L" ";
+ method += ' ';
}
}
if (methodId < kNumMethods)
@@ -296,7 +296,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case NFileHeader::NCompressionMethod::kLZMA:
method += kLZMAMethod;
if (item.IsLzmaEOS())
- method += L":EOS";
+ method += ":EOS";
break;
case NFileHeader::NCompressionMethod::kBZip2: method += kBZip2Method; break;
case NFileHeader::NCompressionMethod::kJpeg: method += kJpegMethod; break;
@@ -304,7 +304,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case NFileHeader::NCompressionMethod::kPPMd: method += kPPMdMethod; break;
default:
{
- wchar_t s[32];
+ char s[32];
ConvertUInt64ToString(methodId, s);
method += s;
}
@@ -313,7 +313,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
break;
}
case kpidHostOS:
- prop = (item.MadeByVersion.HostOS < kNumHostOSes) ?
+ prop = (item.MadeByVersion.HostOS < sizeof(kHostOS) / sizeof(kHostOS[0])) ?
(kHostOS[item.MadeByVersion.HostOS]) : kUnknownOS;
break;
}
diff --git a/CPP/7zip/Archive/Zip/ZipHeader.h b/CPP/7zip/Archive/Zip/ZipHeader.h
index e974079d..4839f554 100755
--- a/CPP/7zip/Archive/Zip/ZipHeader.h
+++ b/CPP/7zip/Archive/Zip/ZipHeader.h
@@ -93,6 +93,7 @@ namespace NFileHeader
kZip64 = 0x01,
kNTFS = 0x0A,
kStrongEncrypt = 0x17,
+ kUnixTime = 0x5455,
kWzAES = 0x9901
};
}
@@ -103,8 +104,18 @@ namespace NFileHeader
enum
{
kMTime = 0,
- kATime = 1,
- kCTime = 2
+ kATime,
+ kCTime
+ };
+ }
+
+ namespace NUnixTime
+ {
+ enum
+ {
+ kMTime = 0,
+ kATime,
+ kCTime
};
}
diff --git a/CPP/7zip/Archive/Zip/ZipIn.cpp b/CPP/7zip/Archive/Zip/ZipIn.cpp
index 5fb53ef2..e396fe5b 100755
--- a/CPP/7zip/Archive/Zip/ZipIn.cpp
+++ b/CPP/7zip/Archive/Zip/ZipIn.cpp
@@ -2,17 +2,14 @@
#include "StdAfx.h"
-#include "ZipIn.h"
-#include "Windows/Defs.h"
-#include "Common/StringConvert.h"
+#include "../../../../C/CpuArch.h"
+
#include "Common/DynamicBuffer.h"
+
#include "../../Common/LimitedStreams.h"
#include "../../Common/StreamUtils.h"
-extern "C"
-{
- #include "../../../../C/CpuArch.h"
-}
+#include "ZipIn.h"
#define Get16(p) GetUi16(p)
#define Get32(p) GetUi32(p)
@@ -21,10 +18,9 @@ extern "C"
namespace NArchive {
namespace NZip {
-// static const char kEndOfString = '\0';
-
HRESULT CInArchive::Open(IInStream *stream, const UInt64 *searchHeaderSizeLimit)
{
+ _inBufMode = false;
Close();
RINOK(stream->Seek(0, STREAM_SEEK_CUR, &m_StreamStartPosition));
m_Position = m_StreamStartPosition;
@@ -36,6 +32,7 @@ HRESULT CInArchive::Open(IInStream *stream, const UInt64 *searchHeaderSizeLimit)
void CInArchive::Close()
{
+ _inBuffer.ReleaseStream();
m_Stream.Release();
}
@@ -117,13 +114,26 @@ HRESULT CInArchive::FindAndReadMarker(IInStream *stream, const UInt64 *searchHea
HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 *processedSize)
{
size_t realProcessedSize = size;
- HRESULT result = ReadStream(m_Stream, data, &realProcessedSize);
+ HRESULT result = S_OK;
+ if (_inBufMode)
+ {
+ try { realProcessedSize = _inBuffer.ReadBytes((Byte *)data, size); }
+ catch (const CInBufferException &e) { return e.ErrorCode; }
+ }
+ else
+ result = ReadStream(m_Stream, data, &realProcessedSize);
if (processedSize != NULL)
*processedSize = (UInt32)realProcessedSize;
m_Position += realProcessedSize;
return result;
}
+void CInArchive::Skip(UInt64 num)
+{
+ for (UInt64 i = 0; i < num; i++)
+ ReadByte();
+}
+
void CInArchive::IncreaseRealPosition(UInt64 addValue)
{
if (m_Stream->Seek(addValue, STREAM_SEEK_CUR, &m_Position) != S_OK)
@@ -160,51 +170,42 @@ Byte CInArchive::ReadByte()
UInt16 CInArchive::ReadUInt16()
{
- UInt16 value = 0;
- for (int i = 0; i < 2; i++)
- value |= (((UInt16)ReadByte()) << (8 * i));
- return value;
+ Byte buf[2];
+ SafeReadBytes(buf, 2);
+ return Get16(buf);
}
UInt32 CInArchive::ReadUInt32()
{
- UInt32 value = 0;
- for (int i = 0; i < 4; i++)
- value |= (((UInt32)ReadByte()) << (8 * i));
- return value;
+ Byte buf[4];
+ SafeReadBytes(buf, 4);
+ return Get32(buf);
}
UInt64 CInArchive::ReadUInt64()
{
- UInt64 value = 0;
- for (int i = 0; i < 8; i++)
- value |= (((UInt64)ReadByte()) << (8 * i));
- return value;
+ Byte buf[8];
+ SafeReadBytes(buf, 8);
+ return Get64(buf);
}
bool CInArchive::ReadUInt32(UInt32 &value)
{
- value = 0;
- for (int i = 0; i < 4; i++)
- {
- Byte b;
- if (!ReadBytesAndTestSize(&b, 1))
- return false;
- value |= (UInt32(b) << (8 * i));
- }
+ Byte buf[4];
+ if (!ReadBytesAndTestSize(buf, 4))
+ return false;
+ value = Get32(buf);
return true;
}
-
-AString CInArchive::ReadFileName(UInt32 nameSize)
+void CInArchive::ReadFileName(UInt32 nameSize, AString &dest)
{
if (nameSize == 0)
- return AString();
- char *p = m_NameBuffer.GetBuffer(nameSize);
+ dest.Empty();
+ char *p = dest.GetBuffer((int)nameSize);
SafeReadBytes(p, nameSize);
p[nameSize] = 0;
- m_NameBuffer.ReleaseBuffer();
- return m_NameBuffer;
+ dest.ReleaseBuffer();
}
void CInArchive::GetArchiveInfo(CInArchiveInfo &archiveInfo) const
@@ -212,38 +213,6 @@ void CInArchive::GetArchiveInfo(CInArchiveInfo &archiveInfo) const
archiveInfo = m_ArchiveInfo;
}
-/*
-void CInArchive::ThrowIncorrectArchiveException()
-{
- throw CInArchiveException(CInArchiveException::kIncorrectArchive);
-}
-*/
-
-static UInt32 GetUInt32(const Byte *data)
-{
- return
- ((UInt32)(Byte)data[0]) |
- (((UInt32)(Byte)data[1]) << 8) |
- (((UInt32)(Byte)data[2]) << 16) |
- (((UInt32)(Byte)data[3]) << 24);
-}
-
-/*
-static UInt16 GetUInt16(const Byte *data)
-{
- return
- ((UInt16)(Byte)data[0]) |
- (((UInt16)(Byte)data[1]) << 8);
-}
-*/
-
-static UInt64 GetUInt64(const Byte *data)
-{
- return GetUInt32(data) | ((UInt64)GetUInt32(data + 4) << 32);
-}
-
-
-
void CInArchive::ReadExtra(UInt32 extraSize, CExtraBlock &extraBlock,
UInt64 &unpackSize, UInt64 &packSize, UInt64 &localHeaderOffset, UInt32 &diskStartNumber)
{
@@ -301,22 +270,26 @@ void CInArchive::ReadExtra(UInt32 extraSize, CExtraBlock &extraBlock,
}
remain -= dataSize;
}
- IncreaseRealPosition(remain);
+ Skip(remain);
}
HRESULT CInArchive::ReadLocalItem(CItemEx &item)
{
- item.ExtractVersion.Version = ReadByte();
- item.ExtractVersion.HostOS = ReadByte();
- item.Flags = ReadUInt16();
- item.CompressionMethod = ReadUInt16();
- item.Time = ReadUInt32();
- item.FileCRC = ReadUInt32();
- item.PackSize = ReadUInt32();
- item.UnPackSize = ReadUInt32();
- UInt32 fileNameSize = ReadUInt16();
- item.LocalExtraSize = ReadUInt16();
- item.Name = ReadFileName(fileNameSize);
+ const int kBufSize = 26;
+ Byte p[kBufSize];
+ SafeReadBytes(p, kBufSize);
+
+ item.ExtractVersion.Version = p[0];
+ item.ExtractVersion.HostOS = p[1];
+ item.Flags = Get16(p + 2);
+ item.CompressionMethod = Get16(p + 4);
+ item.Time = Get32(p + 6);
+ item.FileCRC = Get32(p + 10);
+ item.PackSize = Get32(p + 14);
+ item.UnPackSize = Get32(p + 18);
+ UInt32 fileNameSize = Get16(p + 22);
+ item.LocalExtraSize = Get16(p + 24);
+ ReadFileName(fileNameSize, item.Name);
item.FileHeaderWithNameSize = 4 + NFileHeader::kLocalBlockSize + fileNameSize;
if (item.LocalExtraSize > 0)
{
@@ -400,16 +373,16 @@ HRESULT CInArchive::ReadLocalItemDescriptor(CItemEx &item)
{
// descriptorSignature field is Info-ZIP's extension
// to Zip specification.
- UInt32 descriptorSignature = GetUInt32(buffer + i);
+ UInt32 descriptorSignature = Get32(buffer + i);
// !!!! It must be fixed for Zip64 archives
- UInt32 descriptorPackSize = GetUInt32(buffer + i + 8);
+ UInt32 descriptorPackSize = Get32(buffer + i + 8);
if (descriptorSignature== NSignature::kDataDescriptor && descriptorPackSize == packedSize + i)
{
descriptorWasFound = true;
- item.FileCRC = GetUInt32(buffer + i + 4);
+ item.FileCRC = Get32(buffer + i + 4);
item.PackSize = descriptorPackSize;
- item.UnPackSize = GetUInt32(buffer + i + 12);
+ item.UnPackSize = Get32(buffer + i + 12);
IncreaseRealPosition(Int64(Int32(0 - (numBytesInBuffer - i - NFileHeader::kDataDescriptorSize))));
break;
}
@@ -487,7 +460,7 @@ HRESULT CInArchive::ReadCdItem(CItemEx &item)
item.InternalAttributes = Get16(p + 32);
item.ExternalAttributes = Get32(p + 34);
item.LocalHeaderPosition = Get32(p + 38);
- item.Name = ReadFileName(headerNameSize);
+ ReadFileName(headerNameSize, item.Name);
if (headerExtraSize > 0)
{
@@ -515,11 +488,11 @@ HRESULT CInArchive::TryEcd64(UInt64 offset, CCdInfo &cdInfo)
Byte buf[kEcd64Size];
if (!ReadBytesAndTestSize(buf, kEcd64Size))
return S_FALSE;
- if (GetUInt32(buf) != NSignature::kZip64EndOfCentralDir)
+ if (Get32(buf) != NSignature::kZip64EndOfCentralDir)
return S_FALSE;
- // cdInfo.NumEntries = GetUInt64(buf + 24);
- cdInfo.Size = GetUInt64(buf + 40);
- cdInfo.Offset = GetUInt64(buf + 48);
+ // cdInfo.NumEntries = Get64(buf + 24);
+ cdInfo.Size = Get64(buf + 40);
+ cdInfo.Offset = Get64(buf + 48);
return S_OK;
}
@@ -540,14 +513,14 @@ HRESULT CInArchive::FindCd(CCdInfo &cdInfo)
return S_FALSE;
for (int i = (int)(bufSize - kEcdSize); i >= 0; i--)
{
- if (GetUInt32(buf + i) == NSignature::kEndOfCentralDir)
+ if (Get32(buf + i) == NSignature::kEndOfCentralDir)
{
if (i >= kZip64EcdLocatorSize)
{
const Byte *locator = buf + i - kZip64EcdLocatorSize;
- if (GetUInt32(locator) == NSignature::kZip64EndOfCentralDirLocator)
+ if (Get32(locator) == NSignature::kZip64EndOfCentralDirLocator)
{
- UInt64 ecd64Offset = GetUInt64(locator + 8);
+ UInt64 ecd64Offset = Get64(locator + 8);
if (TryEcd64(ecd64Offset, cdInfo) == S_OK)
return S_OK;
if (TryEcd64(m_ArchiveInfo.StartPosition + ecd64Offset, cdInfo) == S_OK)
@@ -557,11 +530,11 @@ HRESULT CInArchive::FindCd(CCdInfo &cdInfo)
}
}
}
- if (GetUInt32(buf + i + 4) == 0)
+ if (Get32(buf + i + 4) == 0)
{
// cdInfo.NumEntries = GetUInt16(buf + i + 10);
- cdInfo.Size = GetUInt32(buf + i + 12);
- cdInfo.Offset = GetUInt32(buf + i + 16);
+ cdInfo.Size = Get32(buf + i + 12);
+ cdInfo.Offset = Get32(buf + i + 16);
UInt64 curPos = endPosition - bufSize + i;
UInt64 cdEnd = cdInfo.Size + cdInfo.Offset;
if (curPos > cdEnd)
@@ -579,6 +552,13 @@ HRESULT CInArchive::TryReadCd(CObjectVector<CItemEx> &items, UInt64 cdOffset, UI
RINOK(m_Stream->Seek(cdOffset, STREAM_SEEK_SET, &m_Position));
if (m_Position != cdOffset)
return S_FALSE;
+
+ if (!_inBuffer.Create(1 << 15))
+ return E_OUTOFMEMORY;
+ _inBuffer.SetStream(m_Stream);
+ _inBuffer.Init();
+ _inBufMode = true;
+
while(m_Position - cdOffset < cdSize)
{
if (ReadUInt32() != NSignature::kCentralFileHeader)
@@ -765,6 +745,7 @@ HRESULT CInArchive::ReadHeaders(CObjectVector<CItemEx> &items, CProgressVirt *pr
if (res == S_FALSE)
{
+ _inBufMode = false;
m_ArchiveInfo.Base = 0;
RINOK(m_Stream->Seek(m_ArchiveInfo.StartPosition, STREAM_SEEK_SET, &m_Position));
if (m_Position != m_ArchiveInfo.StartPosition)
@@ -789,7 +770,7 @@ HRESULT CInArchive::ReadHeaders(CObjectVector<CItemEx> &items, CProgressVirt *pr
SafeReadBytes(buf, kBufSize);
ecd64.Parse(buf);
- IncreaseRealPosition(recordSize - kZip64EcdSize);
+ Skip(recordSize - kZip64EcdSize);
if (!ReadUInt32(m_Signature))
return S_FALSE;
if (ecd64.thisDiskNumber != 0 || ecd64.startCDDiskNumber != 0)
@@ -838,6 +819,8 @@ HRESULT CInArchive::ReadHeaders(CObjectVector<CItemEx> &items, CProgressVirt *pr
(!items.IsEmpty())))
return S_FALSE;
+ _inBufMode = false;
+ _inBuffer.Free();
return S_OK;
}
diff --git a/CPP/7zip/Archive/Zip/ZipIn.h b/CPP/7zip/Archive/Zip/ZipIn.h
index 750095d6..5f4fe143 100755
--- a/CPP/7zip/Archive/Zip/ZipIn.h
+++ b/CPP/7zip/Archive/Zip/ZipIn.h
@@ -4,8 +4,11 @@
#define __ZIP_IN_H
#include "Common/MyCom.h"
+
#include "../../IStream.h"
+#include "../../Common/InBuffer.h"
+
#include "ZipHeader.h"
#include "ZipItemEx.h"
@@ -65,13 +68,14 @@ class CInArchive
UInt32 m_Signature;
UInt64 m_StreamStartPosition;
UInt64 m_Position;
- AString m_NameBuffer;
+
+ bool _inBufMode;
+ CInBuffer _inBuffer;
HRESULT Seek(UInt64 offset);
HRESULT FindAndReadMarker(IInStream *stream, const UInt64 *searchHeaderSizeLimit);
- bool ReadUInt32(UInt32 &signature);
- AString ReadFileName(UInt32 nameSize);
+ void ReadFileName(UInt32 nameSize, AString &dest);
HRESULT ReadBytes(void *data, UInt32 size, UInt32 *processedSize);
bool ReadBytesAndTestSize(void *data, UInt32 size);
@@ -81,7 +85,9 @@ class CInArchive
UInt16 ReadUInt16();
UInt32 ReadUInt32();
UInt64 ReadUInt64();
+ bool ReadUInt32(UInt32 &signature);
+ void Skip(UInt64 num);
void IncreaseRealPosition(UInt64 addValue);
void ReadExtra(UInt32 extraSize, CExtraBlock &extraBlock,
diff --git a/CPP/7zip/Archive/Zip/ZipItem.cpp b/CPP/7zip/Archive/Zip/ZipItem.cpp
index 03472d85..139b0129 100755
--- a/CPP/7zip/Archive/Zip/ZipItem.cpp
+++ b/CPP/7zip/Archive/Zip/ZipItem.cpp
@@ -51,6 +51,31 @@ bool CExtraSubBlock::ExtractNtfsTime(int index, FILETIME &ft) const
return false;
}
+bool CExtraSubBlock::ExtractUnixTime(int index, UInt32 &res) const
+{
+ res = 0;
+ UInt32 size = (UInt32)Data.GetCapacity();
+ if (ID != NFileHeader::NExtraID::kUnixTime || size < 5)
+ return false;
+ const Byte *p = (const Byte *)Data;
+ Byte flags = *p++;
+ size--;
+ for (int i = 0; i < 3; i++)
+ if ((flags & (1 << i)) != 0)
+ {
+ if (size < 4)
+ return false;
+ if (index == i)
+ {
+ res = GetUi32(p);
+ return true;
+ }
+ p += 4;
+ size -= 4;
+ }
+ return false;
+}
+
bool CLocalItem::IsDir() const
{
return NItemName::HasTailSlash(Name, GetCodePage());
diff --git a/CPP/7zip/Archive/Zip/ZipItem.h b/CPP/7zip/Archive/Zip/ZipItem.h
index c0f780f8..31f2de73 100755
--- a/CPP/7zip/Archive/Zip/ZipItem.h
+++ b/CPP/7zip/Archive/Zip/ZipItem.h
@@ -28,6 +28,7 @@ struct CExtraSubBlock
UInt16 ID;
CByteBuffer Data;
bool ExtractNtfsTime(int index, FILETIME &ft) const;
+ bool ExtractUnixTime(int index, UInt32 &res) const;
};
struct CWzAesExtraField
@@ -151,6 +152,17 @@ struct CExtraBlock
return false;
}
+ bool GetUnixTime(int index, UInt32 &res) const
+ {
+ for (int i = 0; i < SubBlocks.Size(); i++)
+ {
+ const CExtraSubBlock &sb = SubBlocks[i];
+ if (sb.ID == NFileHeader::NExtraID::kUnixTime)
+ return sb.ExtractUnixTime(index, res);
+ }
+ return false;
+ }
+
/*
bool HasStrongCryptoField() const
{
diff --git a/CPP/7zip/Archive/Zip/ZipRegister.cpp b/CPP/7zip/Archive/Zip/ZipRegister.cpp
index 12db3e44..2fd36950 100755
--- a/CPP/7zip/Archive/Zip/ZipRegister.cpp
+++ b/CPP/7zip/Archive/Zip/ZipRegister.cpp
@@ -13,6 +13,6 @@ static IOutArchive *CreateArcOut() { return new NArchive::NZip::CHandler; }
#endif
static CArcInfo g_ArcInfo =
- { L"Zip", L"zip jar xpi", 0, 1, { 0x50, 0x4B, 0x03, 0x04 }, 4, false, CreateArc, CreateArcOut };
+ { L"Zip", L"zip jar xpi odt ods docx xlsx", 0, 1, { 0x50, 0x4B, 0x03, 0x04 }, 4, false, CreateArc, CreateArcOut };
REGISTER_ARC(Zip)
diff --git a/CPP/7zip/Archive/Zip/ZipUpdate.cpp b/CPP/7zip/Archive/Zip/ZipUpdate.cpp
index 5c7e64db..c76ee488 100755
--- a/CPP/7zip/Archive/Zip/ZipUpdate.cpp
+++ b/CPP/7zip/Archive/Zip/ZipUpdate.cpp
@@ -47,8 +47,7 @@ static HRESULT CopyBlockToArchive(ISequentialInStream *inStream,
{
CMyComPtr<ISequentialOutStream> outStream;
outArchive.CreateStreamForCopying(&outStream);
- CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
- return copyCoder->Code(inStream, outStream, NULL, NULL, progress);
+ return NCompress::CopyStream(inStream, outStream, progress);
}
static HRESULT WriteRange(IInStream *inStream, COutArchive &outArchive,
diff --git a/CPP/7zip/Bundles/Alone/Alone.dsp b/CPP/7zip/Bundles/Alone/Alone.dsp
index fc4e97f0..7c557105 100755
--- a/CPP/7zip/Bundles/Alone/Alone.dsp
+++ b/CPP/7zip/Bundles/Alone/Alone.dsp
@@ -44,7 +44,7 @@ RSC=rc.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
-# ADD CPP /nologo /Gz /MT /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MT /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE RSC /l 0x419 /d "NDEBUG"
# ADD RSC /l 0x419 /d "NDEBUG"
BSC32=bscmake.exe
@@ -69,7 +69,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
-# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE RSC /l 0x419 /d "_DEBUG"
# ADD RSC /l 0x419 /d "_DEBUG"
BSC32=bscmake.exe
@@ -94,7 +94,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MD /W3 /GX /O2 /D "NDEBUG" /D "WIN32" /D "_CONSOLE" /D "EXCLUDE_COM" /D "NO_REGISTRY" /D "FORMAT_7Z" /D "FORMAT_BZIP2" /D "FORMAT_ZIP" /D "FORMAT_TAR" /D "FORMAT_GZIP" /D "COMPRESS_LZMA" /D "COMPRESS_BCJ_X86" /D "COMPRESS_BCJ2" /D "COMPRESS_COPY" /D "COMPRESS_MF_PAT" /D "COMPRESS_MF_BT" /D "COMPRESS_PPMD" /D "COMPRESS_DEFLATE" /D "COMPRESS_IMPLODE" /D "COMPRESS_BZIP2" /D "CRYPTO_ZIP" /Yu"StdAfx.h" /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "UNICODE" /D "_UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "UNICODE" /D "_UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE RSC /l 0x419 /d "NDEBUG"
# ADD RSC /l 0x419 /d "NDEBUG"
BSC32=bscmake.exe
@@ -121,7 +121,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "_DEBUG" /D "WIN32" /D "_CONSOLE" /D "EXCLUDE_COM" /D "NO_REGISTRY" /D "FORMAT_7Z" /D "FORMAT_BZIP2" /D "FORMAT_ZIP" /D "FORMAT_TAR" /D "FORMAT_GZIP" /D "COMPRESS_LZMA" /D "COMPRESS_BCJ_X86" /D "COMPRESS_BCJ2" /D "COMPRESS_COPY" /D "COMPRESS_MF_PAT" /D "COMPRESS_MF_BT" /D "COMPRESS_PPMD" /D "COMPRESS_DEFLATE" /D "COMPRESS_IMPLODE" /D "COMPRESS_BZIP2" /D "CRYPTO_ZIP" /D "_MBCS" /Yu"StdAfx.h" /FD /GZ /c
-# ADD CPP /nologo /Gz /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MF_MT" /D "COMPRESS_MT" /D "COMPRESS_BZIP2_MT" /D "BREAK_HANDLER" /D "_7ZIP_LARGE_PAGES" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE RSC /l 0x419 /d "_DEBUG"
# ADD RSC /l 0x419 /d "_DEBUG"
BSC32=bscmake.exe
@@ -321,14 +321,6 @@ SOURCE=..\..\..\Common\MyVector.h
# End Source File
# Begin Source File
-SOURCE=..\..\..\Common\MyWindows.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\..\Common\MyWindows.h
-# End Source File
-# Begin Source File
-
SOURCE=..\..\..\Common\NewHandler.cpp
# End Source File
# Begin Source File
@@ -337,14 +329,6 @@ SOURCE=..\..\..\Common\NewHandler.h
# End Source File
# Begin Source File
-SOURCE=..\..\..\Common\Random.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\..\Common\Random.h
-# End Source File
-# Begin Source File
-
SOURCE=..\..\..\Common\StdInStream.cpp
# End Source File
# Begin Source File
@@ -533,6 +517,14 @@ SOURCE=..\..\Archive\Common\CrossThreadProgress.h
# End Source File
# Begin Source File
+SOURCE=..\..\Common\CWrappers.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Common\CWrappers.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Common\FilePathAutoRename.cpp
# End Source File
# Begin Source File
@@ -868,7 +860,23 @@ SOURCE=..\..\Compress\ImplodeHuffmanDecoder.h
# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Compress\Lzma.h
+SOURCE=..\..\Compress\Lzma2Decoder.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Decoder.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Encoder.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Encoder.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Register.cpp
# End Source File
# Begin Source File
@@ -1185,7 +1193,7 @@ SOURCE=..\..\Compress\ByteSwap.h
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\ByteSwapRegister.cpp
+SOURCE=..\..\Compress\DeltaFilter.cpp
# End Source File
# Begin Source File
@@ -1315,94 +1323,6 @@ SOURCE=..\..\Archive\7z\7zUpdate.cpp
SOURCE=..\..\Archive\7z\7zUpdate.h
# End Source File
# End Group
-# Begin Group "bz2"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\bz2Register.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Handler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Handler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2HandlerOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Item.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Update.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Update.h
-# End Source File
-# End Group
-# Begin Group "gz"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandlerOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHeader.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHeader.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipIn.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipIn.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipItem.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipOut.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipRegister.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipUpdate.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipUpdate.h
-# End Source File
-# End Group
# Begin Group "tar"
# PROP Default_Filter ""
@@ -1623,22 +1543,6 @@ SOURCE=..\..\Archive\Common\ParseProperties.cpp
SOURCE=..\..\Archive\Common\ParseProperties.h
# End Source File
# End Group
-# Begin Group "split"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitRegister.cpp
-# End Source File
-# End Group
# Begin Group "cab"
# PROP Default_Filter ""
@@ -1683,44 +1587,28 @@ SOURCE=..\..\Archive\Cab\CabItem.h
SOURCE=..\..\Archive\Cab\CabRegister.cpp
# End Source File
# End Group
-# Begin Group "Lzma - Ar"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzma\LzmaArcRegister.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzma\LzmaFiltersDecode.cpp
-# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaFiltersDecode.h
+SOURCE=..\..\Archive\Bz2Handler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaHandler.cpp
+SOURCE=..\..\Archive\GzHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaHandler.h
+SOURCE=..\..\Archive\LzmaHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaIn.cpp
+SOURCE=..\..\Archive\SplitHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaIn.h
+SOURCE=..\..\Archive\XzHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaItem.h
-# End Source File
-# End Group
-# Begin Source File
-
SOURCE=..\..\Archive\ZHandler.cpp
# End Source File
# End Group
@@ -2082,6 +1970,142 @@ SOURCE=..\..\PropID.h
# Begin Group "C"
# PROP Default_Filter ""
+# Begin Group "Xz"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Xz.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Xz.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzCrc64.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzCrc64.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzDec.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzEnc.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzEnc.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzIn.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# End Group
# Begin Source File
SOURCE=..\..\..\..\C\7zCrc.c
@@ -2112,6 +2136,30 @@ SOURCE=..\..\..\..\C\7zCrc.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\7zStream.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\Aes.c
!IF "$(CFG)" == "Alone - Win32 Release"
@@ -2285,6 +2333,34 @@ SOURCE=..\..\..\..\C\CpuArch.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Delta.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Delta.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\HuffEnc.c
!IF "$(CFG)" == "Alone - Win32 Release"
@@ -2377,6 +2453,62 @@ SOURCE=..\..\..\..\C\LzHash.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Lzma2Dec.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Dec.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Enc.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Enc.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\LzmaDec.c
!IF "$(CFG)" == "Alone - Win32 Release"
@@ -2433,6 +2565,34 @@ SOURCE=..\..\..\..\C\LzmaEnc.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\MtCoder.c
+
+!IF "$(CFG)" == "Alone - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 ReleaseU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "Alone - Win32 DebugU"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\MtCoder.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\RotateDefs.h
# End Source File
# Begin Source File
diff --git a/CPP/7zip/Bundles/Alone/makefile b/CPP/7zip/Bundles/Alone/makefile
index 2b948601..5a8a359b 100755
--- a/CPP/7zip/Bundles/Alone/makefile
+++ b/CPP/7zip/Bundles/Alone/makefile
@@ -8,6 +8,7 @@ CFLAGS = $(CFLAGS) -I ../../../ \
-D_7ZIP_LARGE_PAGES \
-DBREAK_HANDLER \
-DBENCH_MT \
+ -DSUPPORT_DEVICE_FILE \
CONSOLE_OBJS = \
$O\ConsoleClose.obj \
@@ -51,6 +52,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\FilePathAutoRename.obj \
$O\FileStreams.obj \
$O\FilterCoder.obj \
@@ -93,6 +95,11 @@ UI_COMMON_OBJS = \
$O\WorkDir.obj \
AR_OBJS = \
+ $O\Bz2Handler.obj \
+ $O\GzHandler.obj \
+ $O\LzmaHandler.obj \
+ $O\SplitHandler.obj \
+ $O\XzHandler.obj \
$O\ZHandler.obj \
AR_COMMON_OBJS = \
@@ -126,12 +133,6 @@ AR_COMMON_OBJS = \
$O\7zUpdate.obj \
$O\7zRegister.obj \
-BZ2_OBJS = \
- $O\BZip2Handler.obj \
- $O\BZip2HandlerOut.obj \
- $O\BZip2Update.obj \
- $O\bz2Register.obj \
-
CAB_OBJS = \
$O\CabBlockInStream.obj \
$O\CabHandler.obj \
@@ -139,26 +140,6 @@ CAB_OBJS = \
$O\CabIn.obj \
$O\CabRegister.obj \
-GZ_OBJS = \
- $O\GZipHandler.obj \
- $O\GZipHandlerOut.obj \
- $O\GZipHeader.obj \
- $O\GZipIn.obj \
- $O\GZipOut.obj \
- $O\GZipUpdate.obj \
- $O\GZipRegister.obj \
-
-LZM_OBJS = \
- $O\LzmaArcRegister.obj \
- $O\LzmaFiltersDecode.obj \
- $O\LzmaHandler.obj \
- $O\LzmaIn.obj \
-
-SPLIT_OBJS = \
- $O\SplitHandler.obj \
- $O\SplitHandlerOut.obj \
- $O\SplitRegister.obj \
-
TAR_OBJS = \
$O\TarHandler.obj \
$O\TarHandlerOut.obj \
@@ -190,7 +171,6 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\BZip2CRC.obj \
$O\BZip2Decoder.obj \
$O\BZip2Encoder.obj \
@@ -201,8 +181,12 @@ COMPRESS_OBJS = \
$O\DeflateDecoder.obj \
$O\DeflateEncoder.obj \
$O\DeflateRegister.obj \
+ $O\DeltaFilter.obj \
$O\ImplodeDecoder.obj \
$O\ImplodeHuffmanDecoder.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Encoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaEncoder.obj \
$O\LzmaRegister.obj \
@@ -233,20 +217,30 @@ CRYPTO_OBJS = \
$O\ZipStrong.obj \
C_OBJS = \
+ $O\7zStream.obj \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
$O\BwtSort.obj \
+ $O\Delta.obj \
$O\HuffEnc.obj \
$O\LzFind.obj \
$O\LzFindMt.obj \
+ $O\Lzma2Dec.obj \
+ $O\Lzma2Enc.obj \
$O\LzmaDec.obj \
$O\LzmaEnc.obj \
+ $O\MtCoder.obj \
+ $O\Sha256.obj \
$O\Sort.obj \
$O\Threads.obj \
- $O\Aes.obj \
- $O\Sha256.obj \
+ $O\Xz.obj \
+ $O\XzCrc64.obj \
+ $O\XzDec.obj \
+ $O\XzEnc.obj \
+ $O\XzIn.obj \
!include "../../Crc2.mak"
@@ -261,11 +255,7 @@ OBJS = \
$(AR_OBJS) \
$(AR_COMMON_OBJS) \
$(7Z_OBJS) \
- $(BZ2_OBJS) \
$(CAB_OBJS) \
- $(GZ_OBJS) \
- $(LZM_OBJS) \
- $(SPLIT_OBJS) \
$(TAR_OBJS) \
$(ZIP_OBJS) \
$(COMPRESS_OBJS) \
@@ -296,16 +286,8 @@ $(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
$(7Z_OBJS): ../../Archive/7z/$(*B).cpp
$(COMPL)
-$(BZ2_OBJS): ../../Archive/BZip2/$(*B).cpp
- $(COMPL)
$(CAB_OBJS): ../../Archive/Cab/$(*B).cpp
$(COMPL)
-$(GZ_OBJS): ../../Archive/GZip/$(*B).cpp
- $(COMPL)
-$(LZM_OBJS): ../../Archive/Lzma/$(*B).cpp
- $(COMPL)
-$(SPLIT_OBJS): ../../Archive/Split/$(*B).cpp
- $(COMPL)
$(TAR_OBJS): ../../Archive/Tar/$(*B).cpp
$(COMPL)
$(ZIP_OBJS): ../../Archive/Zip/$(*B).cpp
diff --git a/CPP/7zip/Bundles/Alone7z/makefile b/CPP/7zip/Bundles/Alone7z/makefile
index d255af78..c2bf482c 100755
--- a/CPP/7zip/Bundles/Alone7z/makefile
+++ b/CPP/7zip/Bundles/Alone7z/makefile
@@ -1,4 +1,4 @@
-PROG = 7za.exe
+PROG = 7zr.exe
LIBS = $(LIBS) user32.lib oleaut32.lib Advapi32.lib
CFLAGS = $(CFLAGS) -I ../../../ \
@@ -53,6 +53,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\FilePathAutoRename.obj \
$O\FileStreams.obj \
$O\InBuffer.obj \
@@ -91,6 +92,11 @@ UI_COMMON_OBJS = \
$O\UpdateProduce.obj \
$O\WorkDir.obj \
+AR_OBJS = \
+ $O\LzmaHandler.obj \
+ $O\SplitHandler.obj \
+ $O\XzHandler.obj \
+
AR_COMMON_OBJS = \
$O\CoderMixer2.obj \
$O\CoderMixer2MT.obj \
@@ -121,17 +127,6 @@ AR_COMMON_OBJS = \
$O\7zSpecStream.obj \
$O\7zUpdate.obj \
-LZM_OBJS = \
- $O\LzmaArcRegister.obj \
- $O\LzmaFiltersDecode.obj \
- $O\LzmaHandler.obj \
- $O\LzmaIn.obj \
-
-SPLIT_OBJS = \
- $O\SplitHandler.obj \
- $O\SplitHandlerOut.obj \
- $O\SplitRegister.obj \
-
COMPRESS_OBJS = \
$O\Bcj2Coder.obj \
$O\Bcj2Register.obj \
@@ -141,9 +136,12 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\CopyCoder.obj \
$O\CopyRegister.obj \
+ $O\DeltaFilter.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Encoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaEncoder.obj \
$O\LzmaRegister.obj \
@@ -153,16 +151,28 @@ LZMA_BENCH_OBJS = \
$O\LzmaBenchCon.obj \
C_OBJS = \
- $O\7zCrc.obj \
+ $O\7zStream.obj \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
$O\Alloc.obj \
- $O\LzmaDec.obj \
- $O\LzmaEnc.obj \
+ $O\Delta.obj \
$O\LzFind.obj \
$O\LzFindMt.obj \
+ $O\Lzma2Dec.obj \
+ $O\Lzma2Enc.obj \
+ $O\LzmaDec.obj \
+ $O\LzmaEnc.obj \
+ $O\MtCoder.obj \
+ $O\Sha256.obj \
$O\Threads.obj \
+ $O\Xz.obj \
+ $O\XzCrc64.obj \
+ $O\XzDec.obj \
+ $O\XzEnc.obj \
+ $O\XzIn.obj \
+
+!include "../../Crc2.mak"
OBJS = \
$O\StdAfx.obj \
@@ -171,10 +181,9 @@ OBJS = \
$(WIN_OBJS) \
$(7ZIP_COMMON_OBJS) \
$(UI_COMMON_OBJS) \
+ $(AR_OBJS) \
$(AR_COMMON_OBJS) \
$(7Z_OBJS) \
- $(LZM_OBJS) \
- $(SPLIT_OBJS) \
$(COMPRESS_OBJS) \
$(LZMA_BENCH_OBJS) \
$(C_OBJS) \
@@ -195,18 +204,17 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(UI_COMMON_OBJS): ../../UI/Common/$(*B).cpp
$(COMPL)
+$(AR_OBJS): ../../Archive/$(*B).cpp
+ $(COMPL)
$(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
$(COMPL)
$(7Z_OBJS): ../../Archive/7z/$(*B).cpp
$(COMPL)
-$(LZM_OBJS): ../../Archive/Lzma/$(*B).cpp
- $(COMPL)
-$(SPLIT_OBJS): ../../Archive/Split/$(*B).cpp
- $(COMPL)
$(COMPRESS_OBJS): ../../Compress/$(*B).cpp
$(COMPL_O2)
$(LZMA_BENCH_OBJS): ../../Compress/LZMA_Alone/$(*B).cpp
$(COMPL)
$(C_OBJS): ../../../../C/$(*B).c
$(COMPL_O2)
+!include "../../Crc.mak"
diff --git a/CPP/7zip/Bundles/Format7z/makefile b/CPP/7zip/Bundles/Format7z/makefile
index 65be7a0c..e26aeadd 100755
--- a/CPP/7zip/Bundles/Format7z/makefile
+++ b/CPP/7zip/Bundles/Format7z/makefile
@@ -28,6 +28,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\InBuffer.obj \
$O\InOutTempBuffer.obj \
$O\FilterCoder.obj \
@@ -86,7 +87,6 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\BZip2Crc.obj \
$O\BZip2Decoder.obj \
$O\BZip2Encoder.obj \
@@ -96,6 +96,10 @@ COMPRESS_OBJS = \
$O\DeflateDecoder.obj \
$O\DeflateEncoder.obj \
$O\DeflateRegister.obj \
+ $O\DeltaFilter.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Encoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaEncoder.obj \
$O\LzmaRegister.obj \
@@ -112,20 +116,24 @@ CRYPTO_OBJS = \
$O\Sha1.obj \
C_OBJS = \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
$O\BwtSort.obj \
+ $O\Delta.obj \
$O\HuffEnc.obj \
$O\LzFind.obj \
$O\LzFindMt.obj \
+ $O\Lzma2Dec.obj \
+ $O\Lzma2Enc.obj \
$O\LzmaDec.obj \
$O\LzmaEnc.obj \
+ $O\MtCoder.obj \
+ $O\Sha256.obj \
$O\Sort.obj \
$O\Threads.obj \
- $O\Aes.obj \
- $O\Sha256.obj \
!include "../../Crc2.mak"
diff --git a/CPP/7zip/Bundles/Format7zExtract/makefile b/CPP/7zip/Bundles/Format7zExtract/makefile
index c8ef3df8..c2dd4f7f 100755
--- a/CPP/7zip/Bundles/Format7zExtract/makefile
+++ b/CPP/7zip/Bundles/Format7zExtract/makefile
@@ -26,6 +26,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\InBuffer.obj \
$O\InOutTempBuffer.obj \
$O\FilterCoder.obj \
@@ -74,7 +75,6 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\BZip2Crc.obj \
$O\BZip2Decoder.obj \
$O\BZip2Register.obj \
@@ -82,6 +82,9 @@ COMPRESS_OBJS = \
$O\CopyRegister.obj \
$O\DeflateDecoder.obj \
$O\DeflateRegister.obj \
+ $O\DeltaFilter.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaRegister.obj \
$O\LzOutWindow.obj \
@@ -94,14 +97,16 @@ CRYPTO_OBJS = \
$O\MyAes.obj \
C_OBJS = \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
+ $O\Delta.obj \
+ $O\Lzma2Dec.obj \
$O\LzmaDec.obj \
- $O\Threads.obj \
- $O\Aes.obj \
$O\Sha256.obj \
+ $O\Threads.obj \
!include "../../Crc2.mak"
diff --git a/CPP/7zip/Bundles/Format7zExtractR/makefile b/CPP/7zip/Bundles/Format7zExtractR/makefile
index f544083b..9f06ca5a 100755
--- a/CPP/7zip/Bundles/Format7zExtractR/makefile
+++ b/CPP/7zip/Bundles/Format7zExtractR/makefile
@@ -26,6 +26,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\InBuffer.obj \
$O\InOutTempBuffer.obj \
$O\FilterCoder.obj \
@@ -76,9 +77,11 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\CopyCoder.obj \
$O\CopyRegister.obj \
+ $O\DeltaFilter.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaRegister.obj \
@@ -88,6 +91,8 @@ C_OBJS = \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
+ $O\Delta.obj \
+ $O\Lzma2Dec.obj \
$O\LzmaDec.obj \
$O\Threads.obj \
diff --git a/CPP/7zip/Bundles/Format7zF/Format7z.dsp b/CPP/7zip/Bundles/Format7zF/Format7z.dsp
index c80e4f64..33caaf95 100755
--- a/CPP/7zip/Bundles/Format7zF/Format7z.dsp
+++ b/CPP/7zip/Bundles/Format7zF/Format7z.dsp
@@ -124,6 +124,10 @@ SOURCE=..\..\Archive\Icons\dmg.ico
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\Icons\fat.ico
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\Icons\gz.ico
# End Source File
# Begin Source File
@@ -144,6 +148,10 @@ SOURCE=..\..\Archive\Icons\lzma.ico
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\Icons\ntfs.ico
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\Icons\rar.ico
# End Source File
# Begin Source File
@@ -160,6 +168,10 @@ SOURCE=..\..\Archive\Icons\tar.ico
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\Icons\vhd.ico
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\Icons\wim.ico
# End Source File
# Begin Source File
@@ -168,6 +180,10 @@ SOURCE=..\..\Archive\Icons\xar.ico
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\Icons\xz.ico
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\Icons\z.ico
# End Source File
# Begin Source File
@@ -593,23 +609,35 @@ SOURCE=..\..\Compress\ByteSwap.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\ByteSwap.h
+SOURCE=..\..\Compress\CopyCoder.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\ByteSwapRegister.cpp
+SOURCE=..\..\Compress\CopyCoder.h
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\CopyCoder.cpp
+SOURCE=..\..\Compress\CopyRegister.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\CopyCoder.h
+SOURCE=..\..\Compress\Lzma2Decoder.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Compress\CopyRegister.cpp
+SOURCE=..\..\Compress\Lzma2Decoder.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Encoder.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Encoder.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Register.cpp
# End Source File
# Begin Source File
@@ -690,6 +718,10 @@ SOURCE=..\..\Compress\ArjDecoder2.h
# End Source File
# Begin Source File
+SOURCE=..\..\Compress\DeltaFilter.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Compress\HuffmanDecoder.h
# End Source File
# Begin Source File
@@ -896,6 +928,14 @@ SOURCE=..\..\Common\CreateCoder.h
# End Source File
# Begin Source File
+SOURCE=..\..\Common\CWrappers.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Common\CWrappers.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Common\FilterCoder.cpp
# End Source File
# Begin Source File
@@ -1042,6 +1082,100 @@ SOURCE=..\..\Common\VirtThread.h
# Begin Group "C"
# PROP Default_Filter ""
+# Begin Group "xz"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Xz.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /W4
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# ADD CPP /W4 /WX
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Xz.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzCrc64.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /W4 /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# ADD CPP /W4 /WX
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzCrc64.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzDec.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /W4
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# ADD CPP /W4 /WX
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzEnc.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzEnc.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\XzIn.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /W4
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# ADD CPP /W4 /WX
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# End Group
+# Begin Source File
+
+SOURCE=..\..\..\..\C\7zBuf2.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
# Begin Source File
SOURCE=..\..\..\..\C\7zCrc.c
@@ -1064,6 +1198,11 @@ SOURCE=..\..\..\..\C\7zCrc.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\7zStream.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\Aes.c
!IF "$(CFG)" == "7z - Win32 Release"
@@ -1169,6 +1308,15 @@ SOURCE=..\..\..\..\C\CpuArch.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Delta.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Delta.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\HuffEnc.c
!IF "$(CFG)" == "7z - Win32 Release"
@@ -1233,6 +1381,46 @@ SOURCE=..\..\..\..\C\LzHash.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Lzma2Dec.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Dec.h
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Enc.c
+
+!IF "$(CFG)" == "7z - Win32 Release"
+
+# ADD CPP /O2
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ELSEIF "$(CFG)" == "7z - Win32 Debug"
+
+# SUBTRACT CPP /YX /Yc /Yu
+
+!ENDIF
+
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Enc.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\LzmaDec.c
!IF "$(CFG)" == "7z - Win32 Release"
@@ -1273,6 +1461,15 @@ SOURCE=..\..\..\..\C\LzmaEnc.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\MtCoder.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\MtCoder.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\RotateDefs.h
# End Source File
# Begin Source File
@@ -1500,38 +1697,6 @@ SOURCE=..\..\Archive\Rar\RarVolumeInStream.cpp
SOURCE=..\..\Archive\Rar\RarVolumeInStream.h
# End Source File
# End Group
-# Begin Group "bz2"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\bz2Register.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Handler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Handler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2HandlerOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Item.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Update.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\BZip2\BZip2Update.h
-# End Source File
-# End Group
# Begin Group "Cab"
# PROP Default_Filter ""
@@ -1700,98 +1865,6 @@ SOURCE=..\..\Archive\Common\ParseProperties.cpp
SOURCE=..\..\Archive\Common\ParseProperties.h
# End Source File
# End Group
-# Begin Group "Cpio"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioHeader.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioHeader.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioIn.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioIn.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioItem.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Cpio\CpioRegister.cpp
-# End Source File
-# End Group
-# Begin Group "GZip"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHandlerOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHeader.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipHeader.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipIn.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipIn.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipItem.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipOut.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipRegister.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipUpdate.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\GZip\GZipUpdate.h
-# End Source File
-# End Group
# Begin Group "Iso"
# PROP Default_Filter ""
@@ -1828,54 +1901,6 @@ SOURCE=..\..\Archive\Iso\IsoItem.h
SOURCE=..\..\Archive\Iso\IsoRegister.cpp
# End Source File
# End Group
-# Begin Group "Lzh"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhCRC.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhCRC.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhHeader.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhIn.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhIn.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhItem.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhOutStreamWithCRC.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhOutStreamWithCRC.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Lzh\LzhRegister.cpp
-# End Source File
-# End Group
# Begin Group "Nsis"
# PROP Default_Filter ""
@@ -1908,30 +1933,6 @@ SOURCE=..\..\Archive\Nsis\NsisIn.h
SOURCE=..\..\Archive\Nsis\NsisRegister.cpp
# End Source File
# End Group
-# Begin Group "RPM"
-
-# PROP Default_Filter ""
-# End Group
-# Begin Group "Split"
-
-# PROP Default_Filter ""
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitHandler.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitHandler.h
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitHandlerOut.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\Archive\Split\SplitRegister.cpp
-# End Source File
-# End Group
# Begin Group "Tar"
# PROP Default_Filter ""
@@ -2112,117 +2113,113 @@ SOURCE=..\..\Archive\Com\ComIn.h
SOURCE=..\..\Archive\Com\ComRegister.cpp
# End Source File
# End Group
-# Begin Group "Lzma Ar"
+# Begin Group "Hfs"
# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaArcRegister.cpp
+SOURCE=..\..\Archive\Hfs\HfsHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaFiltersDecode.cpp
+SOURCE=..\..\Archive\Hfs\HfsHandler.h
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaFiltersDecode.h
+SOURCE=..\..\Archive\Hfs\HfsIn.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaHandler.cpp
+SOURCE=..\..\Archive\Hfs\HfsIn.h
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaHandler.h
+SOURCE=..\..\Archive\Hfs\HfsRegister.cpp
# End Source File
+# End Group
+# Begin Group "Udf"
+
+# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaIn.cpp
+SOURCE=..\..\Archive\Udf\UdfHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaIn.h
+SOURCE=..\..\Archive\Udf\UdfHandler.h
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Lzma\LzmaItem.h
+SOURCE=..\..\Archive\Udf\UdfIn.cpp
# End Source File
-# End Group
-# Begin Group "Hfs"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Archive\Hfs\HfsHandler.cpp
+SOURCE=..\..\Archive\Udf\UdfIn.h
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Hfs\HfsHandler.h
+SOURCE=..\..\Archive\Udf\UdfRegister.cpp
# End Source File
+# End Group
# Begin Source File
-SOURCE=..\..\Archive\Hfs\HfsIn.cpp
+SOURCE=..\..\Archive\ArjHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Hfs\HfsIn.h
+SOURCE=..\..\Archive\Bz2Handler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Hfs\HfsRegister.cpp
+SOURCE=..\..\Archive\CpioHandler.cpp
# End Source File
-# End Group
-# Begin Group "Udf"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\..\Archive\Udf\UdfHandler.cpp
+SOURCE=..\..\Archive\DebHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Udf\UdfHandler.h
+SOURCE=..\..\Archive\DmgHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Udf\UdfIn.cpp
+SOURCE=..\..\Archive\ElfHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Udf\UdfIn.h
+SOURCE=..\..\Archive\FatHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\Udf\UdfRegister.cpp
+SOURCE=..\..\Archive\GzHandler.cpp
# End Source File
-# End Group
# Begin Source File
-SOURCE=..\..\Archive\ArjHandler.cpp
+SOURCE=..\..\Archive\IArchive.h
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\DebHandler.cpp
+SOURCE=..\..\Archive\LzhHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\DmgHandler.cpp
+SOURCE=..\..\Archive\LzmaHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\ElfHandler.cpp
+SOURCE=..\..\Archive\MachoHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\IArchive.h
+SOURCE=..\..\Archive\MbrHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\MachoHandler.cpp
+SOURCE=..\..\Archive\MubHandler.cpp
# End Source File
# Begin Source File
-SOURCE=..\..\Archive\MubHandler.cpp
+SOURCE=..\..\Archive\NtfsHandler.cpp
# End Source File
# Begin Source File
@@ -2234,10 +2231,22 @@ SOURCE=..\..\Archive\RpmHandler.cpp
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\SplitHandler.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\VhdHandler.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\XarHandler.cpp
# End Source File
# Begin Source File
+SOURCE=..\..\Archive\XzHandler.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Archive\ZHandler.cpp
# End Source File
# End Group
diff --git a/CPP/7zip/Bundles/Format7zF/makefile b/CPP/7zip/Bundles/Format7zF/makefile
index 18a2d731..a1f09365 100755
--- a/CPP/7zip/Bundles/Format7zF/makefile
+++ b/CPP/7zip/Bundles/Format7zF/makefile
@@ -35,6 +35,7 @@ WIN_OBJS = \
$O\InBuffer.obj \
$O\InOutTempBuffer.obj \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\FilterCoder.obj \
$O\LimitedStreams.obj \
$O\LockedStream.obj \
@@ -55,14 +56,25 @@ AR_OBJS = \
$O\ArchiveExports.obj \
$O\DllExports2.obj \
$O\ArjHandler.obj \
+ $O\Bz2Handler.obj \
+ $O\CpioHandler.obj \
$O\DebHandler.obj \
$O\DmgHandler.obj \
$O\ElfHandler.obj \
+ $O\FatHandler.obj \
+ $O\GzHandler.obj \
+ $O\LzhHandler.obj \
+ $O\LzmaHandler.obj \
$O\MachoHandler.obj \
+ $O\MbrHandler.obj \
$O\MubHandler.obj \
+ $O\NtfsHandler.obj \
$O\PeHandler.obj \
$O\RpmHandler.obj \
+ $O\SplitHandler.obj \
+ $O\VhdHandler.obj \
$O\XarHandler.obj \
+ $O\XzHandler.obj \
$O\ZHandler.obj \
AR_COMMON_OBJS = \
@@ -97,12 +109,6 @@ AR_COMMON_OBJS = \
$O\7zUpdate.obj \
$O\7zRegister.obj \
-BZ2_OBJS = \
- $O\BZip2Handler.obj \
- $O\BZip2HandlerOut.obj \
- $O\BZip2Update.obj \
- $O\bz2Register.obj \
-
CAB_OBJS = \
$O\CabBlockInStream.obj \
$O\CabHandler.obj \
@@ -121,21 +127,6 @@ COM_OBJS = \
$O\ComIn.obj \
$O\ComRegister.obj \
-CPIO_OBJS = \
- $O\CpioHandler.obj \
- $O\CpioHeader.obj \
- $O\CpioIn.obj \
- $O\CpioRegister.obj \
-
-GZ_OBJS = \
- $O\GZipHandler.obj \
- $O\GZipHandlerOut.obj \
- $O\GZipHeader.obj \
- $O\GZipIn.obj \
- $O\GZipOut.obj \
- $O\GZipUpdate.obj \
- $O\GZipRegister.obj \
-
HFS_OBJS = \
$O\HfsHandler.obj \
$O\HfsIn.obj \
@@ -147,19 +138,6 @@ ISO_OBJS = \
$O\IsoIn.obj \
$O\IsoRegister.obj \
-LZH_OBJS = \
- $O\LzhCRC.obj \
- $O\LzhHandler.obj \
- $O\LzhIn.obj \
- $O\LzhOutStreamWithCRC.obj \
- $O\LzhRegister.obj \
-
-LZM_OBJS = \
- $O\LzmaArcRegister.obj \
- $O\LzmaFiltersDecode.obj \
- $O\LzmaHandler.obj \
- $O\LzmaIn.obj \
-
NSIS_OBJS = \
$O\NsisDecode.obj \
$O\NsisHandler.obj \
@@ -174,11 +152,6 @@ RAR_OBJS = \
$O\RarVolumeInStream.obj \
$O\RarRegister.obj \
-SPLIT_OBJS = \
- $O\SplitHandler.obj \
- $O\SplitHandlerOut.obj \
- $O\SplitRegister.obj \
-
TAR_OBJS = \
$O\TarHandler.obj \
$O\TarHandlerOut.obj \
@@ -222,7 +195,6 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\BZip2Crc.obj \
$O\BZip2Decoder.obj \
$O\BZip2Encoder.obj \
@@ -234,9 +206,13 @@ COMPRESS_OBJS = \
$O\DeflateEncoder.obj \
$O\DeflateNsisRegister.obj \
$O\DeflateRegister.obj \
+ $O\DeltaFilter.obj \
$O\ImplodeDecoder.obj \
$O\ImplodeHuffmanDecoder.obj \
$O\LzhDecoder.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Encoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaEncoder.obj \
$O\LzmaRegister.obj \
@@ -272,20 +248,31 @@ CRYPTO_OBJS = \
C_OBJS = \
+ $O\7zBuf2.obj \
+ $O\7zStream.obj \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
$O\BwtSort.obj \
+ $O\Delta.obj \
$O\HuffEnc.obj \
$O\LzFind.obj \
$O\LzFindMt.obj \
+ $O\Lzma2Dec.obj \
+ $O\Lzma2Enc.obj \
$O\LzmaDec.obj \
$O\LzmaEnc.obj \
+ $O\MtCoder.obj \
+ $O\Sha256.obj \
$O\Sort.obj \
$O\Threads.obj \
- $O\Aes.obj \
- $O\Sha256.obj \
+ $O\Xz.obj \
+ $O\XzCrc64.obj \
+ $O\XzDec.obj \
+ $O\XzEnc.obj \
+ $O\XzIn.obj \
!include "../../Crc2.mak"
@@ -298,19 +285,13 @@ OBJS = \
$(AR_OBJS) \
$(AR_COMMON_OBJS) \
$(7Z_OBJS) \
- $(BZ2_OBJS) \
$(CAB_OBJS) \
$(CHM_OBJS) \
$(COM_OBJS) \
- $(CPIO_OBJS) \
- $(GZ_OBJS) \
$(HFS_OBJS) \
$(ISO_OBJS) \
- $(LZH_OBJS) \
- $(LZM_OBJS) \
$(NSIS_OBJS) \
$(RAR_OBJS) \
- $(SPLIT_OBJS) \
$(TAR_OBJS) \
$(UDF_OBJS) \
$(WIM_OBJS) \
@@ -337,32 +318,20 @@ $(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
$(7Z_OBJS): ../../Archive/7z/$(*B).cpp
$(COMPL)
-$(BZ2_OBJS): ../../Archive/BZip2/$(*B).cpp
- $(COMPL)
$(CAB_OBJS): ../../Archive/Cab/$(*B).cpp
$(COMPL)
$(CHM_OBJS): ../../Archive/Chm/$(*B).cpp
$(COMPL)
$(COM_OBJS): ../../Archive/Com/$(*B).cpp
$(COMPL)
-$(CPIO_OBJS): ../../Archive/Cpio/$(*B).cpp
- $(COMPL)
-$(GZ_OBJS): ../../Archive/GZip/$(*B).cpp
- $(COMPL)
$(HFS_OBJS): ../../Archive/Hfs/$(*B).cpp
$(COMPL)
$(ISO_OBJS): ../../Archive/Iso/$(*B).cpp
$(COMPL)
-$(LZH_OBJS): ../../Archive/Lzh/$(*B).cpp
- $(COMPL)
-$(LZM_OBJS): ../../Archive/Lzma/$(*B).cpp
- $(COMPL)
$(NSIS_OBJS): ../../Archive/Nsis/$(*B).cpp
$(COMPL)
$(RAR_OBJS): ../../Archive/Rar/$(*B).cpp
$(COMPL)
-$(SPLIT_OBJS): ../../Archive/Split/$(*B).cpp
- $(COMPL)
$(TAR_OBJS): ../../Archive/Tar/$(*B).cpp
$(COMPL)
$(UDF_OBJS): ../../Archive/Udf/$(*B).cpp
diff --git a/CPP/7zip/Bundles/Format7zF/resource.rc b/CPP/7zip/Bundles/Format7zF/resource.rc
index 79ef2950..babd1149 100755
--- a/CPP/7zip/Bundles/Format7zF/resource.rc
+++ b/CPP/7zip/Bundles/Format7zF/resource.rc
@@ -23,10 +23,14 @@ MY_VERSION_INFO_DLL("7z Standalone Plugin", "7za")
17 ICON "../../Archive/Icons/dmg.ico"
18 ICON "../../Archive/Icons/hfs.ico"
19 ICON "../../Archive/Icons/xar.ico"
+20 ICON "../../Archive/Icons/vhd.ico"
+21 ICON "../../Archive/Icons/fat.ico"
+22 ICON "../../Archive/Icons/ntfs.ico"
+23 ICON "../../Archive/Icons/xz.ico"
STRINGTABLE
BEGIN
- 100 "7z:0 zip:1 bz2:2 bzip2:2 tbz2:2 tbz:2 rar:3 arj:4 z:5 taz:5 lzh:6 lha:6 cab:7 iso:8 split:9 rpm:10 deb:11 cpio:12 tar:13 gz:14 gzip:14 tgz:14 tpz:14 wim:15 swm:15 lzma:16 dmg:17 hfs:18 xar:19"
+ 100 "7z:0 zip:1 bz2:2 bzip2:2 tbz2:2 tbz:2 rar:3 arj:4 z:5 taz:5 lzh:6 lha:6 cab:7 iso:8 split:9 rpm:10 deb:11 cpio:12 tar:13 gz:14 gzip:14 tgz:14 tpz:14 wim:15 swm:15 lzma:16 dmg:17 hfs:18 xar:19 vhd:20 fat:21 ntfs:22 xz:23"
END
diff --git a/CPP/7zip/Bundles/Format7zR/makefile b/CPP/7zip/Bundles/Format7zR/makefile
index b103f2a6..77544ce2 100755
--- a/CPP/7zip/Bundles/Format7zR/makefile
+++ b/CPP/7zip/Bundles/Format7zR/makefile
@@ -26,6 +26,7 @@ WIN_OBJS = \
7ZIP_COMMON_OBJS = \
$O\CreateCoder.obj \
+ $O\CWrappers.obj \
$O\InBuffer.obj \
$O\InOutTempBuffer.obj \
$O\FilterCoder.obj \
@@ -83,9 +84,12 @@ COMPRESS_OBJS = \
$O\BranchMisc.obj \
$O\BranchRegister.obj \
$O\ByteSwap.obj \
- $O\ByteSwapRegister.obj \
$O\CopyCoder.obj \
$O\CopyRegister.obj \
+ $O\DeltaFilter.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Encoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaEncoder.obj \
$O\LzmaRegister.obj \
@@ -96,10 +100,14 @@ C_OBJS = \
$O\Bra.obj \
$O\Bra86.obj \
$O\BraIA64.obj \
+ $O\Delta.obj \
$O\LzFind.obj \
$O\LzFindMt.obj \
+ $O\Lzma2Dec.obj \
+ $O\Lzma2Enc.obj \
$O\LzmaDec.obj \
$O\LzmaEnc.obj \
+ $O\MtCoder.obj \
$O\Threads.obj \
OBJS = \
diff --git a/CPP/7zip/Bundles/SFXCon/Main.cpp b/CPP/7zip/Bundles/SFXCon/Main.cpp
index ac8c1cdf..140f8364 100755
--- a/CPP/7zip/Bundles/SFXCon/Main.cpp
+++ b/CPP/7zip/Bundles/SFXCon/Main.cpp
@@ -5,26 +5,15 @@
#include "Common/MyInitGuid.h"
#include "Common/CommandLineParser.h"
-#include "Common/MyCom.h"
#include "Common/MyException.h"
-#include "Common/StdOutStream.h"
-#include "Common/StringConvert.h"
-#include "Common/Wildcard.h"
-#include "Windows/Defs.h"
-#include "Windows/FileName.h"
#ifdef _WIN32
#include "Windows/DLL.h"
#include "Windows/FileDir.h"
#endif
-#include "../../IPassword.h"
-#include "../../ICoder.h"
-
-#include "../../UI/Common/DefaultName.h"
#include "../../UI/Common/ExitCode.h"
#include "../../UI/Common/Extract.h"
-#include "../../UI/Common/OpenArchive.h"
#include "../../UI/Console/ExtractCallbackConsole.h"
#include "../../UI/Console/List.h"
@@ -36,6 +25,7 @@ using namespace NWindows;
using namespace NFile;
using namespace NCommandLineParser;
+int g_CodePage = -1;
extern CStdOutStream *g_StdStream;
static const char *kCopyrightString =
@@ -343,10 +333,7 @@ int Main2(
if(passwordEnabled)
password = parser[NKey::kPassword].PostStrings[0];
- NFind::CFileInfoW archiveFileInfo;
- if (!NFind::FindFile(arcPath, archiveFileInfo))
- throw kCantFindSFX;
- if (archiveFileInfo.IsDir())
+ if (!NFind::DoesFileExist(arcPath))
throw kCantFindSFX;
UString outputDir;
@@ -380,14 +367,21 @@ int Main2(
CExtractCallbackConsole *ecs = new CExtractCallbackConsole;
CMyComPtr<IFolderArchiveExtractCallback> extractCallback = ecs;
ecs->OutStream = g_StdStream;
+
+ #ifndef _NO_CRYPTO
ecs->PasswordIsDefined = passwordEnabled;
ecs->Password = password;
+ #endif
+
ecs->Init();
COpenCallbackConsole openCallback;
openCallback.OutStream = g_StdStream;
+
+ #ifndef _NO_CRYPTO
openCallback.PasswordIsDefined = passwordEnabled;
openCallback.Password = password;
+ #endif
CExtractOptions eo;
eo.StdOutMode = false;
@@ -429,11 +423,14 @@ int Main2(
UInt64 numErrors = 0;
HRESULT result = ListArchives(
codecs, CIntVector(),
+ false,
v1, v2,
wildcardCensorHead,
true, false,
- passwordEnabled,
- password, numErrors);
+ #ifndef _NO_CRYPTO
+ passwordEnabled, password,
+ #endif
+ numErrors);
if (numErrors > 0)
{
g_StdOut << endl << "Errors: " << numErrors;
diff --git a/CPP/7zip/Bundles/SFXCon/SFXCon.dsp b/CPP/7zip/Bundles/SFXCon/SFXCon.dsp
index 8dc222a5..c4e367f6 100755
--- a/CPP/7zip/Bundles/SFXCon/SFXCon.dsp
+++ b/CPP/7zip/Bundles/SFXCon/SFXCon.dsp
@@ -285,6 +285,14 @@ SOURCE=..\..\Compress\CopyRegister.cpp
# End Source File
# Begin Source File
+SOURCE=..\..\Compress\Lzma2Decoder.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Register.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Compress\LzmaDecoder.cpp
# End Source File
# Begin Source File
@@ -477,6 +485,14 @@ SOURCE=..\..\..\Common\StringConvert.h
# End Source File
# Begin Source File
+SOURCE=..\..\..\Common\UTFConvert.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\Common\UTFConvert.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\Common\Wildcard.cpp
# End Source File
# Begin Source File
@@ -721,6 +737,15 @@ SOURCE=..\..\..\..\C\Bra86.c
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Lzma2Dec.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Dec.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\LzmaDec.c
# SUBTRACT CPP /YX /Yc /Yu
# End Source File
diff --git a/CPP/7zip/Bundles/SFXCon/makefile b/CPP/7zip/Bundles/SFXCon/makefile
index a18aa7ac..cac6d6ef 100755
--- a/CPP/7zip/Bundles/SFXCon/makefile
+++ b/CPP/7zip/Bundles/SFXCon/makefile
@@ -27,6 +27,7 @@ COMMON_OBJS = \
$O\StringConvert.obj \
$O\MyVector.obj \
$O\Wildcard.obj \
+ $O\UTFConvert.obj \
WIN_OBJS = \
$O\DLL.obj \
@@ -89,6 +90,8 @@ COMPRESS_OBJS = \
$O\BcjRegister.obj \
$O\CopyCoder.obj \
$O\CopyRegister.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaRegister.obj \
$O\PpmdDecoder.obj \
@@ -100,12 +103,13 @@ CRYPTO_OBJS = \
$O\MyAes.obj \
C_OBJS = \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra86.obj \
+ $O\Lzma2Dec.obj \
$O\LzmaDec.obj \
- $O\Threads.obj \
- $O\Aes.obj \
$O\Sha256.obj \
+ $O\Threads.obj \
!include "../../Crc2.mak"
diff --git a/CPP/7zip/Bundles/SFXSetup/ExtractCallback.cpp b/CPP/7zip/Bundles/SFXSetup/ExtractCallback.cpp
index 5ec72dc4..8ebe2504 100755
--- a/CPP/7zip/Bundles/SFXSetup/ExtractCallback.cpp
+++ b/CPP/7zip/Bundles/SFXSetup/ExtractCallback.cpp
@@ -2,14 +2,14 @@
#include "StdAfx.h"
-#include "ExtractCallback.h"
-
#include "Common/Wildcard.h"
#include "Windows/FileDir.h"
#include "Windows/FileFind.h"
#include "Windows/PropVariant.h"
+#include "ExtractCallback.h"
+
using namespace NWindows;
using namespace NFile;
@@ -167,7 +167,7 @@ STDMETHODIMP CExtractCallbackImp::GetStream(UInt32 index,
}
NFind::CFileInfoW fileInfo;
- if (NFind::FindFile(fullProcessedPath, fileInfo))
+ if (fileInfo.Find(fullProcessedPath))
{
if (!NDirectory::DeleteFileAlways(fullProcessedPath))
{
diff --git a/CPP/7zip/Bundles/SFXSetup/ExtractEngine.cpp b/CPP/7zip/Bundles/SFXSetup/ExtractEngine.cpp
index d867b74a..e5353c21 100755
--- a/CPP/7zip/Bundles/SFXSetup/ExtractEngine.cpp
+++ b/CPP/7zip/Bundles/SFXSetup/ExtractEngine.cpp
@@ -2,12 +2,7 @@
#include "StdAfx.h"
-#include "ExtractEngine.h"
-
-#include "Common/StringConvert.h"
-
#include "Windows/FileDir.h"
-#include "Windows/FileFind.h"
#include "Windows/Thread.h"
#include "../../UI/Common/OpenArchive.h"
@@ -15,6 +10,7 @@
#include "../../UI/FileManager/FormatUtils.h"
#include "ExtractCallback.h"
+#include "ExtractEngine.h"
using namespace NWindows;
@@ -40,18 +36,18 @@ struct CThreadExtracting
void Process()
{
NFile::NFind::CFileInfoW fi;
- if (!NFile::NFind::FindFile(FileName, fi))
+ if (!fi.Find(FileName))
{
ErrorMessage = kCantFindArchive;
Result = E_FAIL;
return;
}
- Result = MyOpenArchive(Codecs, CIntVector(), FileName, ArchiveLink, ExtractCallbackSpec);
+ Result = ArchiveLink.Open2(Codecs, CIntVector(), false, NULL, FileName, ExtractCallbackSpec);
if (Result != S_OK)
{
if (Result != S_OK)
- ErrorMessage = kCantOpenArchive;
+ ErrorMessage = kCantOpenArchive;
return;
}
diff --git a/CPP/7zip/Bundles/SFXSetup/Main.cpp b/CPP/7zip/Bundles/SFXSetup/Main.cpp
index 3f048710..ece6e3de 100755
--- a/CPP/7zip/Bundles/SFXSetup/Main.cpp
+++ b/CPP/7zip/Bundles/SFXSetup/Main.cpp
@@ -4,25 +4,18 @@
#include <initguid.h>
+#include "Common/CommandLineParser.h"
#include "Common/StringConvert.h"
-#include "Common/Random.h"
#include "Common/TextConfig.h"
-#include "Common/CommandLineParser.h"
+#include "Windows/DLL.h"
#include "Windows/FileDir.h"
-#include "Windows/FileIO.h"
#include "Windows/FileFind.h"
-#include "Windows/FileName.h"
-#include "Windows/DLL.h"
+#include "Windows/FileIO.h"
#include "Windows/ResourceString.h"
-#include "../../IPassword.h"
-#include "../../ICoder.h"
-#include "../../Archive/IArchive.h"
#include "../../UI/Explorer/MyMessages.h"
-// #include "../../UI/GUI/ExtractGUI.h"
-
#include "ExtractEngine.h"
#include "resource.h"
diff --git a/CPP/7zip/Bundles/SFXWin/Main.cpp b/CPP/7zip/Bundles/SFXWin/Main.cpp
index 7cc70882..a538960b 100755
--- a/CPP/7zip/Bundles/SFXWin/Main.cpp
+++ b/CPP/7zip/Bundles/SFXWin/Main.cpp
@@ -100,9 +100,12 @@ int APIENTRY WinMain2()
CExtractCallbackImp *ecs = new CExtractCallbackImp;
CMyComPtr<IFolderArchiveExtractCallback> extractCallback = ecs;
ecs->Init();
+
+ #ifndef _NO_CRYPTO
ecs->PasswordIsDefined = !password.IsEmpty();
ecs->Password = password;
-
+ #endif
+
CExtractOptions eo;
eo.OutputDir = outputFolderDefined ? outputFolder :
fullPath.Left(fileNamePartStartIndex);
diff --git a/CPP/7zip/Bundles/SFXWin/SFXWin.dsp b/CPP/7zip/Bundles/SFXWin/SFXWin.dsp
index fdb33a85..ddd7c5fa 100755
--- a/CPP/7zip/Bundles/SFXWin/SFXWin.dsp
+++ b/CPP/7zip/Bundles/SFXWin/SFXWin.dsp
@@ -261,6 +261,14 @@ SOURCE=..\..\Compress\CopyRegister.cpp
# End Source File
# Begin Source File
+SOURCE=..\..\Compress\Lzma2Decoder.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Compress\Lzma2Register.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Compress\LzmaDecoder.cpp
# End Source File
# Begin Source File
@@ -789,6 +797,15 @@ SOURCE=..\..\..\..\C\Bra86.c
# End Source File
# Begin Source File
+SOURCE=..\..\..\..\C\Lzma2Dec.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\Lzma2Dec.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\LzmaDec.c
# SUBTRACT CPP /YX /Yc /Yu
# End Source File
diff --git a/CPP/7zip/Bundles/SFXWin/makefile b/CPP/7zip/Bundles/SFXWin/makefile
index 8302b7d0..ec0b8590 100755
--- a/CPP/7zip/Bundles/SFXWin/makefile
+++ b/CPP/7zip/Bundles/SFXWin/makefile
@@ -97,6 +97,8 @@ COMPRESS_OBJS = \
$O\BcjRegister.obj \
$O\CopyCoder.obj \
$O\CopyRegister.obj \
+ $O\Lzma2Decoder.obj \
+ $O\Lzma2Register.obj \
$O\LzmaDecoder.obj \
$O\LzmaRegister.obj \
$O\PpmdDecoder.obj \
@@ -108,12 +110,13 @@ CRYPTO_OBJS = \
$O\MyAes.obj \
C_OBJS = \
+ $O\Aes.obj \
$O\Alloc.obj \
$O\Bra86.obj \
+ $O\Lzma2Dec.obj \
$O\LzmaDec.obj \
- $O\Threads.obj \
- $O\Aes.obj \
$O\Sha256.obj \
+ $O\Threads.obj \
!include "../../Crc2.mak"
diff --git a/CPP/7zip/Common/CWrappers.cpp b/CPP/7zip/Common/CWrappers.cpp
new file mode 100755
index 00000000..d440027d
--- /dev/null
+++ b/CPP/7zip/Common/CWrappers.cpp
@@ -0,0 +1,127 @@
+// CWrappers.h
+
+#include "StdAfx.h"
+
+#include "CWrappers.h"
+
+#include "StreamUtils.h"
+
+#define PROGRESS_UNKNOWN_VALUE ((UInt64)(Int64)-1)
+
+#define CONVERT_PR_VAL(x) (x == PROGRESS_UNKNOWN_VALUE ? NULL : &x)
+
+static SRes CompressProgress(void *pp, UInt64 inSize, UInt64 outSize)
+{
+ CCompressProgressWrap *p = (CCompressProgressWrap *)pp;
+ p->Res = p->Progress->SetRatioInfo(CONVERT_PR_VAL(inSize), CONVERT_PR_VAL(outSize));
+ return (SRes)p->Res;
+}
+
+CCompressProgressWrap::CCompressProgressWrap(ICompressProgressInfo *progress)
+{
+ p.Progress = CompressProgress;
+ Progress = progress;
+ Res = SZ_OK;
+}
+
+static const UInt32 kStreamStepSize = (UInt32)1 << 31;
+
+SRes HRESULT_To_SRes(HRESULT res, SRes defaultRes)
+{
+ switch(res)
+ {
+ case S_OK: return SZ_OK;
+ case E_OUTOFMEMORY: return SZ_ERROR_MEM;
+ case E_INVALIDARG: return SZ_ERROR_PARAM;
+ case E_ABORT: return SZ_ERROR_PROGRESS;
+ case S_FALSE: return SZ_ERROR_DATA;
+ }
+ return defaultRes;
+}
+
+static SRes MyRead(void *object, void *data, size_t *size)
+{
+ CSeqInStreamWrap *p = (CSeqInStreamWrap *)object;
+ UInt32 curSize = ((*size < kStreamStepSize) ? (UInt32)*size : kStreamStepSize);
+ p->Res = (p->Stream->Read(data, curSize, &curSize));
+ *size = curSize;
+ if (p->Res == S_OK)
+ return SZ_OK;
+ return HRESULT_To_SRes(p->Res, SZ_ERROR_READ);
+}
+
+static size_t MyWrite(void *object, const void *data, size_t size)
+{
+ CSeqOutStreamWrap *p = (CSeqOutStreamWrap *)object;
+ if (p->Stream)
+ {
+ p->Res = WriteStream(p->Stream, data, size);
+ if (p->Res != 0)
+ return 0;
+ }
+ else
+ p->Res = S_OK;
+ p->Processed += size;
+ return size;
+}
+
+CSeqInStreamWrap::CSeqInStreamWrap(ISequentialInStream *stream)
+{
+ p.Read = MyRead;
+ Stream = stream;
+}
+
+CSeqOutStreamWrap::CSeqOutStreamWrap(ISequentialOutStream *stream)
+{
+ p.Write = MyWrite;
+ Stream = stream;
+ Res = SZ_OK;
+ Processed = 0;
+}
+
+HRESULT SResToHRESULT(SRes res)
+{
+ switch(res)
+ {
+ case SZ_OK: return S_OK;
+ case SZ_ERROR_MEM: return E_OUTOFMEMORY;
+ case SZ_ERROR_PARAM: return E_INVALIDARG;
+ case SZ_ERROR_PROGRESS: return E_ABORT;
+ case SZ_ERROR_DATA: return S_FALSE;
+ }
+ return E_FAIL;
+}
+
+static SRes InStreamWrap_Read(void *pp, void *data, size_t *size)
+{
+ CSeekInStreamWrap *p = (CSeekInStreamWrap *)pp;
+ UInt32 curSize = ((*size < kStreamStepSize) ? (UInt32)*size : kStreamStepSize);
+ p->Res = p->Stream->Read(data, curSize, &curSize);
+ *size = curSize;
+ return (p->Res == S_OK) ? SZ_OK : SZ_ERROR_READ;
+}
+
+static SRes InStreamWrap_Seek(void *pp, Int64 *offset, ESzSeek origin)
+{
+ CSeekInStreamWrap *p = (CSeekInStreamWrap *)pp;
+ UInt32 moveMethod;
+ switch(origin)
+ {
+ case SZ_SEEK_SET: moveMethod = STREAM_SEEK_SET; break;
+ case SZ_SEEK_CUR: moveMethod = STREAM_SEEK_CUR; break;
+ case SZ_SEEK_END: moveMethod = STREAM_SEEK_END; break;
+ default: return SZ_ERROR_PARAM;
+ }
+ UInt64 newPosition;
+ p->Res = p->Stream->Seek(*offset, moveMethod, &newPosition);
+ *offset = (Int64)newPosition;
+ return (p->Res == S_OK) ? SZ_OK : SZ_ERROR_READ;
+}
+
+CSeekInStreamWrap::CSeekInStreamWrap(IInStream *stream)
+{
+ Stream = stream;
+ p.Read = InStreamWrap_Read;
+ p.Seek = InStreamWrap_Seek;
+ Res = S_OK;
+}
diff --git a/CPP/7zip/Common/CWrappers.h b/CPP/7zip/Common/CWrappers.h
new file mode 100755
index 00000000..f7ac96cb
--- /dev/null
+++ b/CPP/7zip/Common/CWrappers.h
@@ -0,0 +1,46 @@
+// CWrappers.h
+
+#ifndef __C_WRAPPERS_H
+#define __C_WRAPPERS_H
+
+#include "../../../C/Types.h"
+
+#include "../ICoder.h"
+#include "../../Common/MyCom.h"
+
+struct CCompressProgressWrap
+{
+ ICompressProgress p;
+ ICompressProgressInfo *Progress;
+ HRESULT Res;
+ CCompressProgressWrap(ICompressProgressInfo *progress);
+};
+
+struct CSeqInStreamWrap
+{
+ ISeqInStream p;
+ ISequentialInStream *Stream;
+ HRESULT Res;
+ CSeqInStreamWrap(ISequentialInStream *stream);
+};
+
+struct CSeekInStreamWrap
+{
+ ISeekInStream p;
+ IInStream *Stream;
+ HRESULT Res;
+ CSeekInStreamWrap(IInStream *stream);
+};
+
+struct CSeqOutStreamWrap
+{
+ ISeqOutStream p;
+ ISequentialOutStream *Stream;
+ HRESULT Res;
+ UInt64 Processed;
+ CSeqOutStreamWrap(ISequentialOutStream *stream);
+};
+
+HRESULT SResToHRESULT(SRes res);
+
+#endif
diff --git a/CPP/7zip/Common/FilePathAutoRename.cpp b/CPP/7zip/Common/FilePathAutoRename.cpp
index bf69fc79..7d6e36f1 100755
--- a/CPP/7zip/Common/FilePathAutoRename.cpp
+++ b/CPP/7zip/Common/FilePathAutoRename.cpp
@@ -1,25 +1,25 @@
// FilePathAutoRename.cpp
#include "StdAfx.h"
-#include "FilePathAutoRename.h"
#include "Common/Defs.h"
#include "Common/IntToString.h"
-#include "Windows/FileName.h"
#include "Windows/FileFind.h"
+#include "FilePathAutoRename.h"
+
using namespace NWindows;
static bool MakeAutoName(const UString &name,
- const UString &extension, int value, UString &path)
+ const UString &extension, unsigned value, UString &path)
{
- wchar_t number[32];
- ConvertUInt64ToString(value, number);
+ wchar_t number[16];
+ ConvertUInt32ToString(value, number);
path = name;
path += number;
path += extension;
- return NFile::NFind::DoesFileExist(path);
+ return NFile::NFind::DoesFileOrDirExist(path);
}
bool AutoRenamePath(UString &fullProcessedPath)
@@ -34,7 +34,7 @@ bool AutoRenamePath(UString &fullProcessedPath)
#endif
UString name, extension;
- if (dotPos > slashPos && dotPos > 0)
+ if (dotPos > slashPos && dotPos > 0)
{
name = fullProcessedPath.Left(dotPos);
extension = fullProcessedPath.Mid(dotPos);
@@ -42,16 +42,14 @@ bool AutoRenamePath(UString &fullProcessedPath)
else
name = fullProcessedPath;
name += L'_';
- int indexLeft = 1, indexRight = (1 << 30);
- while (indexLeft != indexRight)
+ unsigned left = 1, right = (1 << 30);
+ while (left != right)
{
- int indexMid = (indexLeft + indexRight) / 2;
- if (MakeAutoName(name, extension, indexMid, path))
- indexLeft = indexMid + 1;
+ unsigned mid = (left + right) / 2;
+ if (MakeAutoName(name, extension, mid, path))
+ left = mid + 1;
else
- indexRight = indexMid;
+ right = mid;
}
- if (MakeAutoName(name, extension, indexRight, fullProcessedPath))
- return false;
- return true;
+ return !MakeAutoName(name, extension, right, fullProcessedPath);
}
diff --git a/CPP/7zip/Common/FileStreams.cpp b/CPP/7zip/Common/FileStreams.cpp
index eb7ad3a2..f7c01d2c 100755
--- a/CPP/7zip/Common/FileStreams.cpp
+++ b/CPP/7zip/Common/FileStreams.cpp
@@ -8,6 +8,11 @@
#include <errno.h>
#endif
+#ifdef SUPPORT_DEVICE_FILE
+#include "../../../C/Alloc.h"
+#include "../../Common/Defs.h"
+#endif
+
#include "FileStreams.h"
static inline HRESULT ConvertBoolToHRESULT(bool result)
@@ -52,24 +57,138 @@ bool CInFileStream::OpenShared(LPCWSTR fileName, bool shareForWrite)
#endif
#endif
+#ifdef SUPPORT_DEVICE_FILE
+
+static const UInt32 kClusterSize = 1 << 18;
+CInFileStream::CInFileStream():
+ VirtPos(0),
+ PhyPos(0),
+ Buffer(0),
+ BufferSize(0)
+{
+}
+
+#endif
+
+CInFileStream::~CInFileStream()
+{
+ #ifdef SUPPORT_DEVICE_FILE
+ MidFree(Buffer);
+ #endif
+}
+
STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
{
#ifdef USE_WIN_FILE
+ #ifdef SUPPORT_DEVICE_FILE
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (size == 0)
+ return S_OK;
+ if (File.IsDeviceFile)
+ {
+ if (File.LengthDefined)
+ {
+ if (VirtPos >= File.Length)
+ return VirtPos == File.Length ? S_OK : E_FAIL;
+ UInt64 rem = File.Length - VirtPos;
+ if (size > rem)
+ size = (UInt32)rem;
+ }
+ for (;;)
+ {
+ const UInt32 mask = kClusterSize - 1;
+ UInt64 mask2 = ~(UInt64)mask;
+ UInt64 alignedPos = VirtPos & mask2;
+ if (BufferSize > 0 && BufferStartPos == alignedPos)
+ {
+ UInt32 pos = (UInt32)VirtPos & mask;
+ if (pos >= BufferSize)
+ return S_OK;
+ UInt32 rem = MyMin(BufferSize - pos, size);
+ memcpy(data, Buffer + pos, rem);
+ VirtPos += rem;
+ if (processedSize != NULL)
+ *processedSize += rem;
+ return S_OK;
+ }
+
+ bool useBuffer = false;
+ if ((VirtPos & mask) != 0 || ((ptrdiff_t)data & mask) != 0 )
+ useBuffer = true;
+ else
+ {
+ UInt64 end = VirtPos + size;
+ if ((end & mask) != 0)
+ {
+ end &= mask2;
+ if (end <= VirtPos)
+ useBuffer = true;
+ else
+ size = (UInt32)(end - VirtPos);
+ }
+ }
+ if (!useBuffer)
+ break;
+ if (alignedPos != PhyPos)
+ {
+ UInt64 realNewPosition;
+ bool result = File.Seek(alignedPos, FILE_BEGIN, realNewPosition);
+ if (!result)
+ return ConvertBoolToHRESULT(result);
+ PhyPos = realNewPosition;
+ }
+
+ BufferStartPos = alignedPos;
+ UInt32 readSize = kClusterSize;
+ if (File.LengthDefined)
+ readSize = (UInt32)MyMin(File.Length - PhyPos, (UInt64)kClusterSize);
+
+ if (Buffer == 0)
+ {
+ Buffer = (Byte *)MidAlloc(kClusterSize);
+ if (Buffer == 0)
+ return E_OUTOFMEMORY;
+ }
+ bool result = File.Read1(Buffer, readSize, BufferSize);
+ if (!result)
+ return ConvertBoolToHRESULT(result);
+
+ if (BufferSize == 0)
+ return S_OK;
+ PhyPos += BufferSize;
+ }
+
+ if (VirtPos != PhyPos)
+ {
+ UInt64 realNewPosition;
+ bool result = File.Seek(VirtPos, FILE_BEGIN, realNewPosition);
+ if (!result)
+ return ConvertBoolToHRESULT(result);
+ PhyPos = VirtPos = realNewPosition;
+ }
+ }
+ #endif
+
UInt32 realProcessedSize;
bool result = File.ReadPart(data, size, realProcessedSize);
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = realProcessedSize;
+ #ifdef SUPPORT_DEVICE_FILE
+ VirtPos += realProcessedSize;
+ PhyPos += realProcessedSize;
+ #endif
return ConvertBoolToHRESULT(result);
#else
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = 0;
ssize_t res = File.Read(data, (size_t)size);
if (res == -1)
return E_FAIL;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = (UInt32)res;
return S_OK;
@@ -80,10 +199,13 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
{
#ifdef _WIN32
- UInt32 realProcessedSize;
- BOOL res = ::ReadFile(GetStdHandle(STD_INPUT_HANDLE),
- data, size, (DWORD *)&realProcessedSize, NULL);
- if(processedSize != NULL)
+
+ DWORD realProcessedSize;
+ UInt32 sizeTemp = (1 << 20);
+ if (sizeTemp > size)
+ sizeTemp = size;
+ BOOL res = ::ReadFile(GetStdHandle(STD_INPUT_HANDLE), data, sizeTemp, &realProcessedSize, NULL);
+ if (processedSize != NULL)
*processedSize = realProcessedSize;
if (res == FALSE && GetLastError() == ERROR_BROKEN_PIPE)
return S_OK;
@@ -91,7 +213,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
#else
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = 0;
ssize_t res;
do
@@ -101,7 +223,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
while (res < 0 && (errno == EINTR));
if (res == -1)
return E_FAIL;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = (UInt32)res;
return S_OK;
@@ -113,14 +235,37 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
UInt64 *newPosition)
{
- if(seekOrigin >= 3)
+ if (seekOrigin >= 3)
return STG_E_INVALIDFUNCTION;
#ifdef USE_WIN_FILE
+ #ifdef SUPPORT_DEVICE_FILE
+ if (File.IsDeviceFile)
+ {
+ UInt64 newVirtPos = offset;
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: break;
+ case STREAM_SEEK_CUR: newVirtPos += VirtPos; break;
+ case STREAM_SEEK_END: newVirtPos += File.Length; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ VirtPos = newVirtPos;
+ if (newPosition)
+ *newPosition = newVirtPos;
+ return S_OK;
+ }
+ #endif
+
UInt64 realNewPosition;
bool result = File.Seek(offset, seekOrigin, realNewPosition);
- if(newPosition != NULL)
+
+ #ifdef SUPPORT_DEVICE_FILE
+ PhyPos = VirtPos = realNewPosition;
+ #endif
+
+ if (newPosition != NULL)
*newPosition = realNewPosition;
return ConvertBoolToHRESULT(result);
@@ -129,7 +274,7 @@ STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
off_t res = File.Seek(offset, seekOrigin);
if (res == -1)
return E_FAIL;
- if(newPosition != NULL)
+ if (newPosition != NULL)
*newPosition = (UInt64)res;
return S_OK;
@@ -157,18 +302,18 @@ STDMETHODIMP COutFileStream::Write(const void *data, UInt32 size, UInt32 *proces
UInt32 realProcessedSize;
bool result = File.WritePart(data, size, realProcessedSize);
ProcessedSize += realProcessedSize;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = realProcessedSize;
return ConvertBoolToHRESULT(result);
#else
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = 0;
ssize_t res = File.Write(data, (size_t)size);
if (res == -1)
return E_FAIL;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = (UInt32)res;
ProcessedSize += res;
return S_OK;
@@ -178,13 +323,13 @@ STDMETHODIMP COutFileStream::Write(const void *data, UInt32 size, UInt32 *proces
STDMETHODIMP COutFileStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
{
- if(seekOrigin >= 3)
+ if (seekOrigin >= 3)
return STG_E_INVALIDFUNCTION;
#ifdef USE_WIN_FILE
UInt64 realNewPosition;
bool result = File.Seek(offset, seekOrigin, realNewPosition);
- if(newPosition != NULL)
+ if (newPosition != NULL)
*newPosition = realNewPosition;
return ConvertBoolToHRESULT(result);
@@ -193,7 +338,7 @@ STDMETHODIMP COutFileStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPo
off_t res = File.Seek(offset, seekOrigin);
if (res == -1)
return E_FAIL;
- if(newPosition != NULL)
+ if (newPosition != NULL)
*newPosition = (UInt64)res;
return S_OK;
@@ -204,7 +349,7 @@ STDMETHODIMP COutFileStream::SetSize(Int64 newSize)
{
#ifdef USE_WIN_FILE
UInt64 currentPos;
- if(!File.Seek(0, FILE_CURRENT, currentPos))
+ if (!File.Seek(0, FILE_CURRENT, currentPos))
return E_FAIL;
bool result = File.SetLength(newSize);
UInt64 currentPos2;
@@ -218,7 +363,7 @@ STDMETHODIMP COutFileStream::SetSize(Int64 newSize)
#ifndef _WIN32_WCE
STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = 0;
#ifdef _WIN32
@@ -235,7 +380,7 @@ STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *pro
data, sizeTemp, (DWORD *)&realProcessedSize, NULL);
size -= realProcessedSize;
data = (const void *)((const Byte *)data + realProcessedSize);
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize += realProcessedSize;
}
return ConvertBoolToHRESULT(res != FALSE);
@@ -250,7 +395,7 @@ STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *pro
while (res < 0 && (errno == EINTR));
if (res == -1)
return E_FAIL;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = (UInt32)res;
return S_OK;
diff --git a/CPP/7zip/Common/FileStreams.h b/CPP/7zip/Common/FileStreams.h
index 361c2199..32869192 100755
--- a/CPP/7zip/Common/FileStreams.h
+++ b/CPP/7zip/Common/FileStreams.h
@@ -13,9 +13,10 @@
#include "../../Common/C_FileIO.h"
#endif
-#include "../IStream.h"
#include "../../Common/MyCom.h"
+#include "../IStream.h"
+
class CInFileStream:
public IInStream,
public IStreamGetSize,
@@ -24,12 +25,22 @@ class CInFileStream:
public:
#ifdef USE_WIN_FILE
NWindows::NFile::NIO::CInFile File;
+ #ifdef SUPPORT_DEVICE_FILE
+ UInt64 VirtPos;
+ UInt64 PhyPos;
+ UInt64 BufferStartPos;
+ Byte *Buffer;
+ UInt32 BufferSize;
+ #endif
#else
NC::NFile::NIO::CInFile File;
#endif
- CInFileStream() {}
- virtual ~CInFileStream() {}
+ virtual ~CInFileStream();
+ #ifdef SUPPORT_DEVICE_FILE
+ CInFileStream();
+ #endif
+
bool Open(LPCTSTR fileName);
#ifdef USE_WIN_FILE
#ifndef _UNICODE
@@ -58,9 +69,6 @@ class CStdInFileStream:
public CMyUnknownImp
{
public:
- // HANDLE File;
- // CStdInFileStream() File(INVALID_HANDLE_VALUE): {}
- // void Open() { File = GetStdHandle(STD_INPUT_HANDLE); };
MY_UNKNOWN_IMP
virtual ~CStdInFileStream() {}
diff --git a/CPP/7zip/Common/FilterCoder.cpp b/CPP/7zip/Common/FilterCoder.cpp
index 6b34260c..d9911085 100755
--- a/CPP/7zip/Common/FilterCoder.cpp
+++ b/CPP/7zip/Common/FilterCoder.cpp
@@ -2,12 +2,11 @@
#include "StdAfx.h"
-#include "FilterCoder.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
+
#include "../../Common/Defs.h"
+
+#include "FilterCoder.h"
#include "StreamUtils.h"
static const UInt32 kBufferSize = 1 << 17;
diff --git a/CPP/7zip/Common/InBuffer.cpp b/CPP/7zip/Common/InBuffer.cpp
index 29e3ea16..03924d2a 100755
--- a/CPP/7zip/Common/InBuffer.cpp
+++ b/CPP/7zip/Common/InBuffer.cpp
@@ -2,12 +2,9 @@
#include "StdAfx.h"
-#include "InBuffer.h"
+#include "../../../C/Alloc.h"
-extern "C"
-{
- #include "../../../C/Alloc.h"
-}
+#include "InBuffer.h"
CInBuffer::CInBuffer():
_buffer(0),
diff --git a/CPP/7zip/Common/InMemStream.h b/CPP/7zip/Common/InMemStream.h
index adc5aadd..ec493977 100755
--- a/CPP/7zip/Common/InMemStream.h
+++ b/CPP/7zip/Common/InMemStream.h
@@ -1,11 +1,14 @@
// InMemStream.h
-#ifndef __INMEMSTREAM_H
-#define __INMEMSTREAM_H
+#ifndef __IN_MEM_STREAM_H
+#define __IN_MEM_STREAM_H
#include <stdio.h>
+#include "../../../C/Alloc.h"
+
#include "../../Common/MyCom.h"
+
#include "MemBlocks.h"
class CIntListCheck
diff --git a/CPP/7zip/Common/LimitedStreams.cpp b/CPP/7zip/Common/LimitedStreams.cpp
index 490aa37b..1837e320 100755
--- a/CPP/7zip/Common/LimitedStreams.cpp
+++ b/CPP/7zip/Common/LimitedStreams.cpp
@@ -17,11 +17,116 @@ STDMETHODIMP CLimitedSequentialInStream::Read(void *data, UInt32 size, UInt32 *p
if (realProcessedSize == 0)
_wasFinished = true;
}
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = realProcessedSize;
return result;
}
+STDMETHODIMP CLimitedInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_virtPos >= _size)
+ return (_virtPos == _size) ? S_OK: E_FAIL;
+ UInt64 rem = _size - _virtPos;
+ if (rem < size)
+ size = (UInt32)rem;
+ UInt64 newPos = _startOffset + _virtPos;
+ if (newPos != _physPos)
+ {
+ _physPos = newPos;
+ RINOK(SeekToPhys());
+ }
+ HRESULT res = _stream->Read(data, size, &size);
+ if (processedSize != NULL)
+ *processedSize = size;
+ _physPos += size;
+ _virtPos += size;
+ return res;
+}
+
+STDMETHODIMP CLimitedInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: _virtPos = offset; break;
+ case STREAM_SEEK_CUR: _virtPos += offset; break;
+ case STREAM_SEEK_END: _virtPos = _size + offset; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (newPosition)
+ *newPosition = _virtPos;
+ return S_OK;
+}
+
+STDMETHODIMP CClusterInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize != NULL)
+ *processedSize = 0;
+ if (_virtPos >= Size)
+ return (_virtPos == Size) ? S_OK: E_FAIL;
+
+ if (_curRem == 0)
+ {
+ UInt32 blockSize = (UInt32)1 << BlockSizeLog;
+ UInt32 virtBlock = (UInt32)(_virtPos >> BlockSizeLog);
+ UInt32 offsetInBlock = (UInt32)_virtPos & (blockSize - 1);
+ UInt32 phyBlock = Vector[virtBlock];
+ UInt64 newPos = StartOffset + ((UInt64)phyBlock << BlockSizeLog) + offsetInBlock;
+ if (newPos != _physPos)
+ {
+ _physPos = newPos;
+ RINOK(SeekToPhys());
+ }
+ _curRem = blockSize - offsetInBlock;
+ for (int i = 1; i < 64 && (virtBlock + i) < (UInt32)Vector.Size() && phyBlock + i == Vector[virtBlock + i]; i++)
+ _curRem += (UInt32)1 << BlockSizeLog;
+ UInt64 rem = Size - _virtPos;
+ if (_curRem > rem)
+ _curRem = (UInt32)rem;
+ }
+ if (size > _curRem)
+ size = _curRem;
+ HRESULT res = Stream->Read(data, size, &size);
+ if (processedSize != NULL)
+ *processedSize = size;
+ _physPos += size;
+ _virtPos += size;
+ _curRem -= size;
+ return res;
+}
+
+STDMETHODIMP CClusterInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
+{
+ UInt64 newVirtPos = offset;
+ switch(seekOrigin)
+ {
+ case STREAM_SEEK_SET: break;
+ case STREAM_SEEK_CUR: newVirtPos += _virtPos; break;
+ case STREAM_SEEK_END: newVirtPos += Size; break;
+ default: return STG_E_INVALIDFUNCTION;
+ }
+ if (_virtPos != newVirtPos)
+ _curRem = 0;
+ _virtPos = newVirtPos;
+ if (newPosition)
+ *newPosition = newVirtPos;
+ return S_OK;
+}
+
+
+HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream)
+{
+ *resStream = 0;
+ CLimitedInStream *streamSpec = new CLimitedInStream;
+ CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
+ streamSpec->SetStream(inStream);
+ RINOK(streamSpec->InitAndSeek(pos, size));
+ streamSpec->SeekToStart();
+ *resStream = streamTemp.Detach();
+ return S_OK;
+}
+
STDMETHODIMP CLimitedSequentialOutStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
HRESULT result = S_OK;
@@ -29,12 +134,16 @@ STDMETHODIMP CLimitedSequentialOutStream::Write(const void *data, UInt32 size, U
*processedSize = 0;
if (size > _size)
{
- size = (UInt32)_size;
- if (size == 0)
+ if (_size == 0)
{
_overflow = true;
- return E_FAIL;
+ if (!_overflowIsAllowed)
+ return E_FAIL;
+ if (processedSize != NULL)
+ *processedSize = size;
+ return S_OK;
}
+ size = (UInt32)_size;
}
if (_stream)
result = _stream->Write(data, size, &size);
diff --git a/CPP/7zip/Common/LimitedStreams.h b/CPP/7zip/Common/LimitedStreams.h
index 9bfdc8eb..f6900d51 100755
--- a/CPP/7zip/Common/LimitedStreams.h
+++ b/CPP/7zip/Common/LimitedStreams.h
@@ -1,9 +1,10 @@
// LimitedStreams.h
-#ifndef __LIMITEDSTREAMS_H
-#define __LIMITEDSTREAMS_H
+#ifndef __LIMITED_STREAMS_H
+#define __LIMITED_STREAMS_H
#include "../../Common/MyCom.h"
+#include "../../Common/MyVector.h"
#include "../IStream.h"
class CLimitedSequentialInStream:
@@ -30,6 +31,73 @@ public:
bool WasFinished() const { return _wasFinished; }
};
+class CLimitedInStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+ CMyComPtr<IInStream> _stream;
+ UInt64 _virtPos;
+ UInt64 _physPos;
+ UInt64 _size;
+ UInt64 _startOffset;
+
+ HRESULT SeekToPhys() { return _stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
+public:
+ void SetStream(IInStream *stream) { _stream = stream; }
+ HRESULT InitAndSeek(UInt64 startOffset, UInt64 size)
+ {
+ _startOffset = startOffset;
+ _physPos = startOffset;
+ _virtPos = 0;
+ _size = size;
+ return SeekToPhys();
+ }
+
+ MY_UNKNOWN_IMP1(IInStream)
+
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+
+ HRESULT SeekToStart() { return Seek(0, STREAM_SEEK_SET, NULL); }
+};
+
+class CClusterInStream:
+ public IInStream,
+ public CMyUnknownImp
+{
+ UInt64 _virtPos;
+ UInt64 _physPos;
+ UInt32 _curRem;
+public:
+ CMyComPtr<IInStream> Stream;
+ UInt64 StartOffset;
+ UInt64 Size;
+ int BlockSizeLog;
+ CRecordVector<UInt32> Vector;
+
+ HRESULT SeekToPhys() { return Stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
+
+ HRESULT InitAndSeek()
+ {
+ _curRem = 0;
+ _virtPos = 0;
+ _physPos = StartOffset;
+ if (Vector.Size() > 0)
+ {
+ _physPos = StartOffset + (Vector[0] << BlockSizeLog);
+ return SeekToPhys();
+ }
+ return S_OK;
+ }
+
+ MY_UNKNOWN_IMP1(IInStream)
+
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
+};
+
+HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream);
+
class CLimitedSequentialOutStream:
public ISequentialOutStream,
public CMyUnknownImp
@@ -37,15 +105,17 @@ class CLimitedSequentialOutStream:
CMyComPtr<ISequentialOutStream> _stream;
UInt64 _size;
bool _overflow;
+ bool _overflowIsAllowed;
public:
MY_UNKNOWN_IMP
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
void SetStream(ISequentialOutStream *stream) { _stream = stream; }
void ReleaseStream() { _stream.Release(); }
- void Init(UInt64 size)
+ void Init(UInt64 size, bool overflowIsAllowed = false)
{
_size = size;
_overflow = false;
+ _overflowIsAllowed = overflowIsAllowed;
}
bool IsFinishedOK() const { return (_size == 0 && !_overflow); }
UInt64 GetRem() const { return _size; }
diff --git a/CPP/7zip/Common/MemBlocks.cpp b/CPP/7zip/Common/MemBlocks.cpp
index baceb163..a5b93b5e 100755
--- a/CPP/7zip/Common/MemBlocks.cpp
+++ b/CPP/7zip/Common/MemBlocks.cpp
@@ -2,10 +2,10 @@
#include "StdAfx.h"
-#include "Common/MyCom.h"
+#include "../../../C/Alloc.h"
-#include "StreamUtils.h"
#include "MemBlocks.h"
+#include "StreamUtils.h"
bool CMemBlockManager::AllocateSpace(size_t numBlocks)
{
diff --git a/CPP/7zip/Common/MemBlocks.h b/CPP/7zip/Common/MemBlocks.h
index dcdc0d82..e1058ae3 100755
--- a/CPP/7zip/Common/MemBlocks.h
+++ b/CPP/7zip/Common/MemBlocks.h
@@ -1,14 +1,8 @@
// MemBlocks.h
-#ifndef __MEMBLOCKS_H
-#define __MEMBLOCKS_H
+#ifndef __MEM_BLOCKS_H
+#define __MEM_BLOCKS_H
-extern "C"
-{
-#include "../../../C/Alloc.h"
-}
-
-#include "Common/Types.h"
#include "Common/MyVector.h"
#include "Windows/Synchronization.h"
diff --git a/CPP/7zip/Common/MethodProps.cpp b/CPP/7zip/Common/MethodProps.cpp
index 86adc6b8..5836d0f8 100755
--- a/CPP/7zip/Common/MethodProps.cpp
+++ b/CPP/7zip/Common/MethodProps.cpp
@@ -8,14 +8,14 @@
#include "MethodProps.h"
-static UInt64 k_LZMA = 0x030101;
-// static UInt64 k_LZMA2 = 0x030102;
+static const UInt64 k_LZMA = 0x030101;
+static const UInt64 k_LZMA2 = 0x21;
HRESULT SetMethodProperties(const CMethod &method, const UInt64 *inSizeForReduce, IUnknown *coder)
{
bool tryReduce = false;
UInt32 reducedDictionarySize = 1 << 10;
- if (inSizeForReduce != 0 && (method.Id == k_LZMA /* || methodFull.MethodID == k_LZMA2 */))
+ if (inSizeForReduce != 0 && (method.Id == k_LZMA || method.Id == k_LZMA2))
{
for (;;)
{
diff --git a/CPP/7zip/Common/OutBuffer.cpp b/CPP/7zip/Common/OutBuffer.cpp
index 998525c3..2e5debd8 100755
--- a/CPP/7zip/Common/OutBuffer.cpp
+++ b/CPP/7zip/Common/OutBuffer.cpp
@@ -1,13 +1,10 @@
-// OutByte.cpp
+// OutBuffer.cpp
#include "StdAfx.h"
-#include "OutBuffer.h"
+#include "../../../C/Alloc.h"
-extern "C"
-{
- #include "../../../C/Alloc.h"
-}
+#include "OutBuffer.h"
bool COutBuffer::Create(UInt32 bufferSize)
{
diff --git a/CPP/7zip/Common/VirtThread.cpp b/CPP/7zip/Common/VirtThread.cpp
index f12581ad..cf39bd02 100755
--- a/CPP/7zip/Common/VirtThread.cpp
+++ b/CPP/7zip/Common/VirtThread.cpp
@@ -40,6 +40,7 @@ CVirtThread::~CVirtThread()
ExitEvent = true;
if (StartEvent.IsCreated())
StartEvent.Set();
- Thread.Wait();
+ if (Thread.IsCreated())
+ Thread.Wait();
}
diff --git a/CPP/7zip/Compress/BZip2Decoder.cpp b/CPP/7zip/Compress/BZip2Decoder.cpp
index c44debf0..ef896f6a 100755
--- a/CPP/7zip/Compress/BZip2Decoder.cpp
+++ b/CPP/7zip/Compress/BZip2Decoder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "../../Common/Defs.h"
@@ -420,15 +417,19 @@ static UInt32 NO_INLINE DecodeBlock2Rand(const UInt32 *tt, UInt32 blockSize, UIn
return crc.GetDigest();
}
-#ifdef COMPRESS_BZIP2_MT
-CDecoder::CDecoder():
- m_States(0)
+CDecoder::CDecoder()
{
+ #ifdef COMPRESS_BZIP2_MT
+ m_States = 0;
m_NumThreadsPrev = 0;
NumThreads = 1;
+ #endif;
+ _needInStreamInit = true;
}
+#ifdef COMPRESS_BZIP2_MT
+
CDecoder::~CDecoder()
{
Free();
@@ -611,43 +612,61 @@ HRESULT CDecoder::DecodeFile(bool &isBZ, ICompressProgressInfo *progress)
}
HRESULT CDecoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgressInfo *progress)
+ bool &isBZ, ICompressProgressInfo *progress)
{
+ isBZ = false;
+ try
+ {
+
if (!m_InStream.Create(kBufferSize))
return E_OUTOFMEMORY;
if (!m_OutStream.Create(kBufferSize))
return E_OUTOFMEMORY;
- m_InStream.SetStream(inStream);
- m_InStream.Init();
+ if (inStream)
+ m_InStream.SetStream(inStream);
+
+ CDecoderFlusher flusher(this, inStream != NULL);
+
+ if (_needInStreamInit)
+ {
+ m_InStream.Init();
+ _needInStreamInit = false;
+ }
+ _inStart = m_InStream.GetProcessedSize();
+
+ m_InStream.AlignToByte();
m_OutStream.SetStream(outStream);
m_OutStream.Init();
- CDecoderFlusher flusher(this);
-
- bool isBZ;
RINOK(DecodeFile(isBZ, progress));
- return isBZ ? S_OK: S_FALSE;
-}
+ flusher.NeedFlush = false;
+ return Flush();
-STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress)
-{
- try { return CodeReal(inStream, outStream, inSize, outSize, progress); }
+ }
catch(const CInBufferException &e) { return e.ErrorCode; }
catch(const COutBufferException &e) { return e.ErrorCode; }
catch(...) { return E_FAIL; }
}
-STDMETHODIMP CDecoder::GetInStreamProcessedSize(UInt64 *value)
+STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgressInfo *progress)
{
- if (value == NULL)
- return E_INVALIDARG;
- *value = m_InStream.GetProcessedSize();
- return S_OK;
+ _needInStreamInit = true;
+ bool isBZ;
+ RINOK(CodeReal(inStream, outStream, isBZ, progress));
+ return isBZ ? S_OK : S_FALSE;
}
+HRESULT CDecoder::CodeResume(ISequentialOutStream *outStream, bool &isBZ, ICompressProgressInfo *progress)
+{
+ return CodeReal(NULL, outStream, isBZ, progress);
+}
+
+STDMETHODIMP CDecoder::SetInStream(ISequentialInStream *inStream) { m_InStream.SetStream(inStream); return S_OK; }
+STDMETHODIMP CDecoder::ReleaseInStream() { m_InStream.ReleaseStream(); return S_OK; }
+
#ifdef COMPRESS_BZIP2_MT
static THREAD_FUNC_DECL MFThread(void *p) { ((CState *)p)->ThreadFunc(); return 0; }
@@ -694,7 +713,7 @@ void CState::ThreadFunc()
nextBlockIndex = 0;
Decoder->NextBlockIndex = nextBlockIndex;
UInt32 crc;
- UInt64 packSize;
+ UInt64 packSize = 0;
UInt32 blockSize = 0, origPtr = 0;
bool randMode = false;
@@ -752,8 +771,9 @@ void CState::ThreadFunc()
{
if (Decoder->Progress)
{
+ UInt64 inSize = packSize - Decoder->_inStart;
UInt64 unpackSize = Decoder->m_OutStream.GetProcessedSize();
- res = Decoder->Progress->SetRatioInfo(&packSize, &unpackSize);
+ res = Decoder->Progress->SetRatioInfo(&inSize, &unpackSize);
}
}
else
diff --git a/CPP/7zip/Compress/BZip2Decoder.h b/CPP/7zip/Compress/BZip2Decoder.h
index 195b6b38..ea06449e 100755
--- a/CPP/7zip/Compress/BZip2Decoder.h
+++ b/CPP/7zip/Compress/BZip2Decoder.h
@@ -62,7 +62,6 @@ class CDecoder :
#ifdef COMPRESS_BZIP2_MT
public ICompressSetCoderMt,
#endif
- public ICompressGetInStreamProcessedSize,
public CMyUnknownImp
{
public:
@@ -71,9 +70,11 @@ public:
NBitm::CDecoder<CInBuffer> m_InStream;
Byte m_Selectors[kNumSelectorsMax];
CHuffmanDecoder m_HuffmanDecoders[kNumTablesMax];
+ UInt64 _inStart;
+
private:
- UInt32 m_NumThreadsPrev;
+ bool _needInStreamInit;
UInt32 ReadBits(int numBits);
Byte ReadByte();
@@ -82,18 +83,22 @@ private:
HRESULT PrepareBlock(CState &state);
HRESULT DecodeFile(bool &isBZ, ICompressProgressInfo *progress);
HRESULT CodeReal(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
+ bool &isBZ, ICompressProgressInfo *progress);
class CDecoderFlusher
{
CDecoder *_decoder;
public:
bool NeedFlush;
- CDecoderFlusher(CDecoder *decoder): _decoder(decoder), NeedFlush(true) {}
+ bool ReleaseInStream;
+ CDecoderFlusher(CDecoder *decoder, bool releaseInStream):
+ _decoder(decoder),
+ ReleaseInStream(releaseInStream),
+ NeedFlush(true) {}
~CDecoderFlusher()
{
if (NeedFlush)
_decoder->Flush();
- _decoder->ReleaseStreams();
+ _decoder->ReleaseStreams(ReleaseInStream);
}
};
@@ -103,6 +108,7 @@ public:
#ifdef COMPRESS_BZIP2_MT
ICompressProgressInfo *Progress;
CState *m_States;
+ UInt32 m_NumThreadsPrev;
NWindows::NSynchronization::CManualResetEvent CanProcessEvent;
NWindows::NSynchronization::CCriticalSection CS;
@@ -118,7 +124,6 @@ public:
HRESULT Result2;
UInt32 BlockSizeMax;
- CDecoder();
~CDecoder();
HRESULT Create();
void Free();
@@ -127,28 +132,37 @@ public:
CState m_States[1];
#endif
+ CDecoder();
+
HRESULT ReadSignatures(bool &wasFinished, UInt32 &crc);
HRESULT Flush() { return m_OutStream.Flush(); }
- void ReleaseStreams()
+ void ReleaseStreams(bool releaseInStream)
{
- m_InStream.ReleaseStream();
+ if (releaseInStream)
+ m_InStream.ReleaseStream();
m_OutStream.ReleaseStream();
}
+ MY_QUERYINTERFACE_BEGIN
#ifdef COMPRESS_BZIP2_MT
- MY_UNKNOWN_IMP2(ICompressSetCoderMt, ICompressGetInStreamProcessedSize)
- #else
- MY_UNKNOWN_IMP1(ICompressGetInStreamProcessedSize)
+ MY_QUERYINTERFACE_ENTRY(ICompressSetCoderMt)
#endif
+ MY_QUERYINTERFACE_END
+ MY_ADDREF_RELEASE
+
STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
- STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
+ STDMETHOD(SetInStream)(ISequentialInStream *inStream);
+ STDMETHOD(ReleaseInStream)();
+ HRESULT CodeResume(ISequentialOutStream *outStream, bool &isBZ, ICompressProgressInfo *progress);
+ UInt64 GetInputProcessedSize() const { return m_InStream.GetProcessedSize(); }
+
#ifdef COMPRESS_BZIP2_MT
STDMETHOD(SetNumberOfThreads)(UInt32 numThreads);
#endif
diff --git a/CPP/7zip/Compress/BZip2Encoder.cpp b/CPP/7zip/Compress/BZip2Encoder.cpp
index ef284a33..0546c15c 100755
--- a/CPP/7zip/Compress/BZip2Encoder.cpp
+++ b/CPP/7zip/Compress/BZip2Encoder.cpp
@@ -2,12 +2,9 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
#include "../../../C/BwtSort.h"
#include "../../../C/HuffEnc.h"
-}
#include "BZip2Crc.h"
#include "BZip2Encoder.h"
@@ -823,7 +820,7 @@ HRESULT CEncoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream *
WriteByte(kFinSig5);
WriteCrc(CombinedCrc.GetDigest());
- return S_OK;
+ return Flush();
}
STDMETHODIMP CEncoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
diff --git a/CPP/7zip/Compress/BZip2Encoder.h b/CPP/7zip/Compress/BZip2Encoder.h
index 1dda0aa8..a79813f3 100755
--- a/CPP/7zip/Compress/BZip2Encoder.h
+++ b/CPP/7zip/Compress/BZip2Encoder.h
@@ -1,4 +1,4 @@
-// Compress/BZip2Encoder.h
+// BZip2Encoder.h
#ifndef __COMPRESS_BZIP2_ENCODER_H
#define __COMPRESS_BZIP2_ENCODER_H
@@ -215,12 +215,9 @@ public:
{
CEncoder *_coder;
public:
- bool NeedFlush;
- CFlusher(CEncoder *coder): _coder(coder), NeedFlush(true) {}
+ CFlusher(CEncoder *coder): _coder(coder) {}
~CFlusher()
{
- if (NeedFlush)
- _coder->Flush();
_coder->ReleaseStreams();
}
};
diff --git a/CPP/7zip/Compress/Bcj2Coder.cpp b/CPP/7zip/Compress/Bcj2Coder.cpp
index e1356abb..13ce5160 100755
--- a/CPP/7zip/Compress/Bcj2Coder.cpp
+++ b/CPP/7zip/Compress/Bcj2Coder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "Bcj2Coder.h"
diff --git a/CPP/7zip/Compress/BcjCoder.h b/CPP/7zip/Compress/BcjCoder.h
index 612bb547..0754bcd2 100755
--- a/CPP/7zip/Compress/BcjCoder.h
+++ b/CPP/7zip/Compress/BcjCoder.h
@@ -3,10 +3,7 @@
#ifndef __COMPRESS_BCJ_CODER_H
#define __COMPRESS_BCJ_CODER_H
-extern "C"
-{
#include "../../../C/Bra.h"
-}
#include "BranchCoder.h"
diff --git a/CPP/7zip/Compress/BitlDecoder.h b/CPP/7zip/Compress/BitlDecoder.h
index 0ccd7154..3bee413a 100755
--- a/CPP/7zip/Compress/BitlDecoder.h
+++ b/CPP/7zip/Compress/BitlDecoder.h
@@ -35,15 +35,11 @@ public:
m_Value = 0;
NumExtraBytes = 0;
}
- UInt64 GetProcessedSize() const
- { return m_Stream.GetProcessedSize() - (kNumBigValueBits - m_BitPos) / 8; }
- UInt64 GetProcessedBitsSize() const
- { return (m_Stream.GetProcessedSize() << 3) - (kNumBigValueBits - m_BitPos); }
- int GetBitPosition() const { return (m_BitPos & 7); }
+ UInt64 GetProcessedSize() const { return m_Stream.GetProcessedSize() + NumExtraBytes - (kNumBigValueBits - m_BitPos) / 8; }
void Normalize()
{
- for (;m_BitPos >= 8; m_BitPos -= 8)
+ for (; m_BitPos >= 8; m_BitPos -= 8)
{
Byte b = 0;
if (!m_Stream.ReadByte(b))
@@ -114,10 +110,31 @@ public:
UInt32 ReadBits(int numBits)
{
Normalize();
- UInt32 res = m_NormalValue & ( (1 << numBits) - 1);
+ UInt32 res = m_NormalValue & ((1 << numBits) - 1);
MovePos(numBits);
return res;
}
+
+ void AlignToByte() { MovePos((32 - this->m_BitPos) & 7); }
+
+ Byte ReadByte()
+ {
+ if (this->m_BitPos == kNumBigValueBits)
+ {
+ Byte b = 0;
+ if (!this->m_Stream.ReadByte(b))
+ {
+ b = 0xFF;
+ this->NumExtraBytes++;
+ }
+ return b;
+ }
+ {
+ Byte b = (Byte)(m_NormalValue & 0xFF);
+ MovePos(8);
+ return b;
+ }
+ }
};
}
diff --git a/CPP/7zip/Compress/BitmDecoder.h b/CPP/7zip/Compress/BitmDecoder.h
index fbe4c949..2885ed78 100755
--- a/CPP/7zip/Compress/BitmDecoder.h
+++ b/CPP/7zip/Compress/BitmDecoder.h
@@ -31,9 +31,7 @@ public:
Normalize();
}
- UInt64 GetProcessedSize() const
- { return m_Stream.GetProcessedSize() - (kNumBigValueBits - m_BitPos) / 8; }
- UInt32 GetBitPosition() const { return (m_BitPos & 7); }
+ UInt64 GetProcessedSize() const { return m_Stream.GetProcessedSize() - (kNumBigValueBits - m_BitPos) / 8; }
void Normalize()
{
@@ -59,6 +57,8 @@ public:
MovePos(numBits);
return res;
}
+
+ void AlignToByte() { MovePos((32 - m_BitPos) & 7); }
};
}
diff --git a/CPP/7zip/Compress/BranchMisc.cpp b/CPP/7zip/Compress/BranchMisc.cpp
index 5a19c44a..423b723a 100755
--- a/CPP/7zip/Compress/BranchMisc.cpp
+++ b/CPP/7zip/Compress/BranchMisc.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Bra.h"
-}
#include "BranchMisc.h"
diff --git a/CPP/7zip/Compress/ByteSwap.cpp b/CPP/7zip/Compress/ByteSwap.cpp
index 3f252f2c..645b6ffc 100755
--- a/CPP/7zip/Compress/ByteSwap.cpp
+++ b/CPP/7zip/Compress/ByteSwap.cpp
@@ -2,7 +2,31 @@
#include "StdAfx.h"
-#include "ByteSwap.h"
+#include "../../Common/MyCom.h"
+
+#include "../ICoder.h"
+
+#include "../Common/RegisterCodec.h"
+
+class CByteSwap2:
+ public ICompressFilter,
+ public CMyUnknownImp
+{
+public:
+ MY_UNKNOWN_IMP
+ STDMETHOD(Init)();
+ STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
+};
+
+class CByteSwap4:
+ public ICompressFilter,
+ public CMyUnknownImp
+{
+public:
+ MY_UNKNOWN_IMP
+ STDMETHOD(Init)();
+ STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
+};
STDMETHODIMP CByteSwap2::Init() { return S_OK; }
@@ -36,3 +60,14 @@ STDMETHODIMP_(UInt32) CByteSwap4::Filter(Byte *data, UInt32 size)
}
return i;
}
+
+static void *CreateCodec2() { return (void *)(ICompressFilter *)(new CByteSwap2); }
+static void *CreateCodec4() { return (void *)(ICompressFilter *)(new CByteSwap4); }
+
+static CCodecInfo g_CodecsInfo[] =
+{
+ { CreateCodec2, CreateCodec2, 0x020302, L"Swap2", 1, true },
+ { CreateCodec4, CreateCodec4, 0x020304, L"Swap4", 1, true }
+};
+
+REGISTER_CODECS(ByteSwap)
diff --git a/CPP/7zip/Compress/ByteSwap.h b/CPP/7zip/Compress/ByteSwap.h
deleted file mode 100755
index f13bec80..00000000
--- a/CPP/7zip/Compress/ByteSwap.h
+++ /dev/null
@@ -1,30 +0,0 @@
-// ByteSwap.h
-
-#ifndef __COMPRESS_BYTE_SWAP_H
-#define __COMPRESS_BYTE_SWAP_H
-
-#include "../../Common/MyCom.h"
-
-#include "../ICoder.h"
-
-class CByteSwap2:
- public ICompressFilter,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP
- STDMETHOD(Init)();
- STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
-};
-
-class CByteSwap4:
- public ICompressFilter,
- public CMyUnknownImp
-{
-public:
- MY_UNKNOWN_IMP
- STDMETHOD(Init)();
- STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
-};
-
-#endif
diff --git a/CPP/7zip/Compress/ByteSwapRegister.cpp b/CPP/7zip/Compress/ByteSwapRegister.cpp
deleted file mode 100755
index e3405ca0..00000000
--- a/CPP/7zip/Compress/ByteSwapRegister.cpp
+++ /dev/null
@@ -1,18 +0,0 @@
-// ByteSwapRegister.cpp
-
-#include "StdAfx.h"
-
-#include "../Common/RegisterCodec.h"
-
-#include "ByteSwap.h"
-
-static void *CreateCodec2() { return (void *)(ICompressFilter *)(new CByteSwap2); }
-static void *CreateCodec4() { return (void *)(ICompressFilter *)(new CByteSwap4); }
-
-static CCodecInfo g_CodecsInfo[] =
-{
- { CreateCodec2, CreateCodec4, 0x020302, L"Swap2", 1, true },
- { CreateCodec4, CreateCodec4, 0x020304, L"Swap4", 1, true }
-};
-
-REGISTER_CODECS(ByteSwap)
diff --git a/CPP/7zip/Compress/CodecExports.cpp b/CPP/7zip/Compress/CodecExports.cpp
index cd7a209c..4ff1c0fc 100755
--- a/CPP/7zip/Compress/CodecExports.cpp
+++ b/CPP/7zip/Compress/CodecExports.cpp
@@ -3,10 +3,13 @@
#include "StdAfx.h"
#include "../../Common/ComTry.h"
+
#include "../../Windows/PropVariant.h"
-#include "../Common/RegisterCodec.h"
+
#include "../ICoder.h"
+#include "../Common/RegisterCodec.h"
+
extern unsigned int g_NumCodecs;
extern const CCodecInfo *g_Codecs[];
diff --git a/CPP/7zip/Compress/CopyCoder.cpp b/CPP/7zip/Compress/CopyCoder.cpp
index 899ffa3a..f71692a7 100755
--- a/CPP/7zip/Compress/CopyCoder.cpp
+++ b/CPP/7zip/Compress/CopyCoder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "../Common/StreamUtils.h"
@@ -35,16 +32,18 @@ STDMETHODIMP CCopyCoder::Code(ISequentialInStream *inStream,
TotalSize = 0;
for (;;)
{
- UInt32 realProcessedSize;
UInt32 size = kBufferSize;
if (outSize != 0)
if (size > *outSize - TotalSize)
size = (UInt32)(*outSize - TotalSize);
- RINOK(inStream->Read(_buffer, size, &realProcessedSize));
- if (realProcessedSize == 0)
+ RINOK(inStream->Read(_buffer, size, &size));
+ if (size == 0)
break;
- RINOK(WriteStream(outStream, _buffer, realProcessedSize));
- TotalSize += realProcessedSize;
+ if (outStream)
+ {
+ RINOK(WriteStream(outStream, _buffer, size));
+ }
+ TotalSize += size;
if (progress != NULL)
{
RINOK(progress->SetRatioInfo(&TotalSize, &TotalSize));
@@ -59,4 +58,10 @@ STDMETHODIMP CCopyCoder::GetInStreamProcessedSize(UInt64 *value)
return S_OK;
}
+HRESULT CopyStream(ISequentialInStream *inStream, ISequentialOutStream *outStream, ICompressProgressInfo *progress)
+{
+ CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
+ return copyCoder->Code(inStream, outStream, NULL, NULL, progress);
+}
+
}
diff --git a/CPP/7zip/Compress/CopyCoder.h b/CPP/7zip/Compress/CopyCoder.h
index c5736781..c5445ccf 100755
--- a/CPP/7zip/Compress/CopyCoder.h
+++ b/CPP/7zip/Compress/CopyCoder.h
@@ -17,7 +17,7 @@ class CCopyCoder:
Byte *_buffer;
public:
UInt64 TotalSize;
- CCopyCoder(): TotalSize(0) , _buffer(0) {};
+ CCopyCoder(): TotalSize(0), _buffer(0) {};
~CCopyCoder();
MY_UNKNOWN_IMP1(ICompressGetInStreamProcessedSize)
@@ -27,6 +27,8 @@ public:
STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
};
+HRESULT CopyStream(ISequentialInStream *inStream, ISequentialOutStream *outStream, ICompressProgressInfo *progress);
+
}
#endif
diff --git a/CPP/7zip/Compress/DeflateDecoder.cpp b/CPP/7zip/Compress/DeflateDecoder.cpp
index dae60c07..cf4a5105 100755
--- a/CPP/7zip/Compress/DeflateDecoder.cpp
+++ b/CPP/7zip/Compress/DeflateDecoder.cpp
@@ -15,6 +15,7 @@ CCoder::CCoder(bool deflate64Mode, bool deflateNSIS):
_deflate64Mode(deflate64Mode),
_deflateNSIS(deflateNSIS),
_keepHistory(false),
+ _needInitInStream(true),
ZlibMode(false) {}
UInt32 CCoder::ReadBits(int numBits)
@@ -70,9 +71,7 @@ bool CCoder::ReadTables(void)
if (blockType == NBlockType::kStored)
{
m_StoredMode = true;
- UInt32 currentBitPosition = m_InBitStream.GetBitPosition();
- int numBitsForAlign = (int)(currentBitPosition > 0 ? (8 - currentBitPosition): 0);
- ReadBits(numBitsForAlign);
+ m_InBitStream.AlignToByte();
m_StoredBlockSize = ReadBits(kStoredBlockLengthFieldSize);
if (_deflateNSIS)
return true;
@@ -130,10 +129,8 @@ HRESULT CCoder::CodeSpec(UInt32 curSize)
if (!_keepHistory)
if (!m_OutWindowStream.Create(_deflate64Mode ? kHistorySize64: kHistorySize32))
return E_OUTOFMEMORY;
- if (!m_InBitStream.Create(1 << 17))
- return E_OUTOFMEMORY;
+ RINOK(InitInStream(_needInitInStream));
m_OutWindowStream.Init(_keepHistory);
- m_InBitStream.Init();
m_FinalBlock = false;
_remainLen = 0;
_needReadTable = true;
@@ -167,7 +164,7 @@ HRESULT CCoder::CodeSpec(UInt32 curSize)
if(m_StoredMode)
{
for (; m_StoredBlockSize > 0 && curSize > 0; m_StoredBlockSize--, curSize--)
- m_OutWindowStream.PutByte((Byte)m_InBitStream.ReadBits(8));
+ m_OutWindowStream.PutByte(m_InBitStream.ReadByte());
_needReadTable = (m_StoredBlockSize == 0);
continue;
}
@@ -231,14 +228,29 @@ HRESULT CCoder::CodeSpec(UInt32 curSize)
return S_OK;
}
-HRESULT CCoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 *, const UInt64 *outSize, ICompressProgressInfo *progress)
+#ifdef _NO_EXCEPTIONS
+
+#define DEFLATE_TRY_BEGIN
+#define DEFLATE_TRY_END
+
+#else
+
+#define DEFLATE_TRY_BEGIN try {
+#define DEFLATE_TRY_END } \
+ catch(const CInBufferException &e) { return e.ErrorCode; } \
+ catch(const CLzOutWindowException &e) { return e.ErrorCode; } \
+ catch(...) { return S_FALSE; }
+
+#endif
+
+HRESULT CCoder::CodeReal(ISequentialOutStream *outStream,
+ const UInt64 *outSize, ICompressProgressInfo *progress)
{
- SetInStream(inStream);
+ DEFLATE_TRY_BEGIN
m_OutWindowStream.SetStream(outStream);
- SetOutStreamSize(outSize);
CCoderReleaser flusher(this);
+ const UInt64 inStart = m_InBitStream.GetProcessedSize();
const UInt64 start = m_OutWindowStream.GetProcessedSize();
for (;;)
{
@@ -256,45 +268,33 @@ HRESULT CCoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream *ou
break;
if (progress != NULL)
{
- const UInt64 inSize = m_InBitStream.GetProcessedSize();
+ const UInt64 inSize = m_InBitStream.GetProcessedSize() - inStart;
const UInt64 nowPos64 = m_OutWindowStream.GetProcessedSize() - start;
RINOK(progress->SetRatioInfo(&inSize, &nowPos64));
}
}
if (_remainLen == kLenIdFinished && ZlibMode)
{
- UInt32 currentBitPosition = m_InBitStream.GetBitPosition();
- int numBitsForAlign = (int)(currentBitPosition > 0 ? (8 - currentBitPosition): 0);
- ReadBits(numBitsForAlign);
+ m_InBitStream.AlignToByte();
for (int i = 0; i < 4; i++)
- ZlibFooter[i] = (Byte)m_InBitStream.ReadBits(8);
+ ZlibFooter[i] = m_InBitStream.ReadByte();
}
flusher.NeedFlush = false;
- return Flush();
+ HRESULT res = Flush();
+ if (res == S_OK && InputEofError())
+ return S_FALSE;
+ return res;
+ DEFLATE_TRY_END
}
-
-#ifdef _NO_EXCEPTIONS
-
-#define DEFLATE_TRY_BEGIN
-#define DEFLATE_TRY_END
-
-#else
-
-#define DEFLATE_TRY_BEGIN try {
-#define DEFLATE_TRY_END } \
- catch(const CInBufferException &e) { return e.ErrorCode; } \
- catch(const CLzOutWindowException &e) { return e.ErrorCode; } \
- catch(...) { return S_FALSE; }
-
-#endif
-
HRESULT CCoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress)
+ const UInt64 * /* inSize */, const UInt64 *outSize, ICompressProgressInfo *progress)
{
- DEFLATE_TRY_BEGIN
- return CodeReal(inStream, outStream, inSize, outSize, progress);
- DEFLATE_TRY_END
+ SetInStream(inStream);
+ SetOutStreamSize(outSize);
+ HRESULT res = CodeReal(outStream, outSize, progress);
+ ReleaseInStream();
+ return res;
}
STDMETHODIMP CCoder::GetInStreamProcessedSize(UInt64 *value)
@@ -320,6 +320,7 @@ STDMETHODIMP CCoder::ReleaseInStream()
STDMETHODIMP CCoder::SetOutStreamSize(const UInt64 * /* outSize */)
{
_remainLen = kLenIdNeedInit;
+ _needInitInStream = true;
m_OutWindowStream.Init(_keepHistory);
return S_OK;
}
@@ -342,4 +343,11 @@ STDMETHODIMP CCoder::Read(void *data, UInt32 size, UInt32 *processedSize)
#endif
+STDMETHODIMP CCoder::CodeResume(ISequentialOutStream *outStream, const UInt64 *outSize, ICompressProgressInfo *progress)
+{
+ _remainLen = kLenIdNeedInit;
+ m_OutWindowStream.Init(_keepHistory);
+ return CodeReal(outStream, outSize, progress);
+}
+
}}}
diff --git a/CPP/7zip/Compress/DeflateDecoder.h b/CPP/7zip/Compress/DeflateDecoder.h
index 796d90a4..56ab2bea 100755
--- a/CPP/7zip/Compress/DeflateDecoder.h
+++ b/CPP/7zip/Compress/DeflateDecoder.h
@@ -44,6 +44,7 @@ class CCoder:
bool _deflateNSIS;
bool _deflate64Mode;
bool _keepHistory;
+ bool _needInitInStream;
Int32 _remainLen;
UInt32 _rep0;
bool _needReadTable;
@@ -53,24 +54,18 @@ class CCoder:
bool DeCodeLevelTable(Byte *values, int numSymbols);
bool ReadTables();
- void ReleaseStreams()
- {
- m_OutWindowStream.ReleaseStream();
- ReleaseInStream();
- }
-
HRESULT Flush() { return m_OutWindowStream.Flush(); }
class CCoderReleaser
{
- CCoder *m_Coder;
+ CCoder *_coder;
public:
bool NeedFlush;
- CCoderReleaser(CCoder *coder): m_Coder(coder), NeedFlush(true) {}
+ CCoderReleaser(CCoder *coder): _coder(coder), NeedFlush(true) {}
~CCoderReleaser()
{
if (NeedFlush)
- m_Coder->Flush();
- m_Coder->ReleaseStreams();
+ _coder->Flush();
+ _coder->ReleaseOutStream();
}
};
friend class CCoderReleaser;
@@ -81,10 +76,17 @@ public:
Byte ZlibFooter[4];
CCoder(bool deflate64Mode, bool deflateNSIS = false);
+ virtual ~CCoder() {};
+
void SetKeepHistory(bool keepHistory) { _keepHistory = keepHistory; }
- HRESULT CodeReal(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
+ void ReleaseOutStream()
+ {
+ m_OutWindowStream.ReleaseStream();
+ }
+
+ HRESULT CodeReal(ISequentialOutStream *outStream,
+ const UInt64 *outSize, ICompressProgressInfo *progress);
#ifndef NO_READ_FROM_CODER
MY_UNKNOWN_IMP4(
@@ -109,6 +111,25 @@ public:
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
#endif
+ STDMETHOD(CodeResume)(ISequentialOutStream *outStream, const UInt64 *outSize, ICompressProgressInfo *progress);
+
+ HRESULT InitInStream(bool needInit)
+ {
+ if (!m_InBitStream.Create(1 << 17))
+ return E_OUTOFMEMORY;
+ if (needInit)
+ {
+ m_InBitStream.Init();
+ _needInitInStream = false;
+ }
+ return S_OK;
+ }
+
+ void AlignToByte() { m_InBitStream.AlignToByte(); }
+ Byte ReadByte() { return (Byte)m_InBitStream.ReadBits(8); }
+ bool InputEofError() const { return m_InBitStream.ExtraBitsWereRead(); }
+ UInt64 GetInputProcessedSize() const { return m_InBitStream.GetProcessedSize(); }
+
// IGetInStreamProcessedSize
STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
};
diff --git a/CPP/7zip/Compress/DeflateEncoder.cpp b/CPP/7zip/Compress/DeflateEncoder.cpp
index b5c70969..28906e8c 100755
--- a/CPP/7zip/Compress/DeflateEncoder.cpp
+++ b/CPP/7zip/Compress/DeflateEncoder.cpp
@@ -2,11 +2,8 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
#include "../../../C/HuffEnc.h"
-}
#include "Common/ComTry.h"
diff --git a/CPP/7zip/Compress/DeflateEncoder.h b/CPP/7zip/Compress/DeflateEncoder.h
index 2790bcc7..71c39e4e 100755
--- a/CPP/7zip/Compress/DeflateEncoder.h
+++ b/CPP/7zip/Compress/DeflateEncoder.h
@@ -3,10 +3,7 @@
#ifndef __DEFLATE_ENCODER_H
#define __DEFLATE_ENCODER_H
-extern "C"
-{
- #include "../../../C/LzFind.h"
-}
+#include "../../../C/LzFind.h"
#include "Common/MyCom.h"
diff --git a/CPP/7zip/Compress/DeltaFilter.cpp b/CPP/7zip/Compress/DeltaFilter.cpp
new file mode 100755
index 00000000..2e421acf
--- /dev/null
+++ b/CPP/7zip/Compress/DeltaFilter.cpp
@@ -0,0 +1,112 @@
+// DeltaFilter.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/Delta.h"
+
+#include "../Common/RegisterCodec.h"
+
+#include "BranchCoder.h"
+
+struct CDelta
+{
+ unsigned _delta;
+ Byte _state[DELTA_STATE_SIZE];
+ CDelta(): _delta(1) {}
+ void DeltaInit() { Delta_Init(_state); }
+};
+
+class CDeltaEncoder:
+ public ICompressFilter,
+ public ICompressSetCoderProperties,
+ public ICompressWriteCoderProperties,
+ CDelta,
+ public CMyUnknownImp
+{
+public:
+ MY_UNKNOWN_IMP2(ICompressSetCoderProperties, ICompressWriteCoderProperties)
+ STDMETHOD(Init)();
+ STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
+ STDMETHOD(SetCoderProperties)(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps);
+ STDMETHOD(WriteCoderProperties)(ISequentialOutStream *outStream);
+};
+
+class CDeltaDecoder:
+ public ICompressFilter,
+ public ICompressSetDecoderProperties2,
+ CDelta,
+ public CMyUnknownImp
+{
+public:
+ MY_UNKNOWN_IMP1(ICompressSetDecoderProperties2)
+ STDMETHOD(Init)();
+ STDMETHOD_(UInt32, Filter)(Byte *data, UInt32 size);
+ STDMETHOD(SetDecoderProperties2)(const Byte *data, UInt32 size);
+};
+
+STDMETHODIMP CDeltaEncoder::Init()
+{
+ DeltaInit();
+ return S_OK;
+}
+
+STDMETHODIMP_(UInt32) CDeltaEncoder::Filter(Byte *data, UInt32 size)
+{
+ Delta_Encode(_state, _delta, data, size);
+ return size;
+}
+
+STDMETHODIMP CDeltaEncoder::SetCoderProperties(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps)
+{
+ UInt32 delta = _delta;
+ for (UInt32 i = 0; i < numProps; i++)
+ {
+ const PROPVARIANT &prop = props[i];
+ if (propIDs[i] != NCoderPropID::kDefaultProp || prop.vt != VT_UI4 || prop.ulVal < 1 || prop.ulVal > 256)
+ return E_INVALIDARG;
+ delta = prop.ulVal;
+ }
+ _delta = delta;
+ return S_OK;
+}
+
+STDMETHODIMP CDeltaEncoder::WriteCoderProperties(ISequentialOutStream *outStream)
+{
+ Byte prop = (Byte)(_delta - 1);
+ return outStream->Write(&prop, 1, NULL);
+}
+
+STDMETHODIMP CDeltaDecoder::Init()
+{
+ DeltaInit();
+ return S_OK;
+}
+
+STDMETHODIMP_(UInt32) CDeltaDecoder::Filter(Byte *data, UInt32 size)
+{
+ Delta_Decode(_state, _delta, data, size);
+ return size;
+}
+
+STDMETHODIMP CDeltaDecoder::SetDecoderProperties2(const Byte *props, UInt32 size)
+{
+ if (size != 1)
+ return E_INVALIDARG;
+ _delta = (unsigned)props[0] + 1;
+ return S_OK;
+}
+
+#define CREATE_CODEC(x) \
+ static void *CreateCodec ## x() { return (void *)(ICompressFilter *)(new C ## x ## Decoder); } \
+ static void *CreateCodec ## x ## Out() { return (void *)(ICompressFilter *)(new C ## x ## Encoder); }
+
+CREATE_CODEC(Delta)
+
+#define METHOD_ITEM(x, id, name) { CreateCodec ## x, CreateCodec ## x ## Out, id, name, 1, true }
+
+static CCodecInfo g_CodecsInfo[] =
+{
+ METHOD_ITEM(Delta, 3, L"Delta")
+};
+
+REGISTER_CODECS(Delta)
diff --git a/CPP/7zip/Compress/LZMA_Alone/AloneLZMA.dsp b/CPP/7zip/Compress/LZMA_Alone/AloneLZMA.dsp
index 76fa7b84..9b005efb 100755
--- a/CPP/7zip/Compress/LZMA_Alone/AloneLZMA.dsp
+++ b/CPP/7zip/Compress/LZMA_Alone/AloneLZMA.dsp
@@ -297,6 +297,14 @@ SOURCE=..\..\..\Common\Types.h
# PROP Default_Filter ""
# Begin Source File
+SOURCE=..\..\Common\CWrappers.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Common\CWrappers.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\Common\FileStreams.cpp
# End Source File
# Begin Source File
diff --git a/CPP/7zip/Compress/LZMA_Alone/LzmaAlone.cpp b/CPP/7zip/Compress/LZMA_Alone/LzmaAlone.cpp
index 4044c86d..3d8e475f 100755
--- a/CPP/7zip/Compress/LZMA_Alone/LzmaAlone.cpp
+++ b/CPP/7zip/Compress/LZMA_Alone/LzmaAlone.cpp
@@ -31,13 +31,10 @@
#include "../../../Windows/System.h"
#endif
-extern "C"
-{
- #include "../../../../C/7zVersion.h"
- #include "../../../../C/Alloc.h"
- #include "../../../../C/LzmaUtil/Lzma86Dec.h"
- #include "../../../../C/LzmaUtil/Lzma86Enc.h"
-}
+#include "../../../../C/7zVersion.h"
+#include "../../../../C/Alloc.h"
+#include "../../../../C/LzmaUtil/Lzma86Dec.h"
+#include "../../../../C/LzmaUtil/Lzma86Enc.h"
using namespace NCommandLineParser;
diff --git a/CPP/7zip/Compress/LZMA_Alone/LzmaBench.cpp b/CPP/7zip/Compress/LZMA_Alone/LzmaBench.cpp
index 2ad9a577..6a325fe0 100755
--- a/CPP/7zip/Compress/LZMA_Alone/LzmaBench.cpp
+++ b/CPP/7zip/Compress/LZMA_Alone/LzmaBench.cpp
@@ -28,11 +28,8 @@
#endif
#endif
-extern "C"
-{
#include "../../../../C/7zCrc.h"
#include "../../../../C/Alloc.h"
-}
#include "../../../Common/MyCom.h"
@@ -575,22 +572,22 @@ HRESULT CEncoderInfo::Init(UInt32 dictionarySize, UInt32 numThreads, CBaseRandom
PROPID propIDs[] =
{
NCoderPropID::kDictionarySize,
- NCoderPropID::kMultiThread
+ NCoderPropID::kNumThreads
};
const int kNumProps = sizeof(propIDs) / sizeof(propIDs[0]);
- PROPVARIANT properties[kNumProps];
- properties[0].vt = VT_UI4;
- properties[0].ulVal = (UInt32)dictionarySize;
+ PROPVARIANT props[kNumProps];
+ props[0].vt = VT_UI4;
+ props[0].ulVal = dictionarySize;
- properties[1].vt = VT_BOOL;
- properties[1].boolVal = (numThreads > 1) ? VARIANT_TRUE : VARIANT_FALSE;
+ props[1].vt = VT_UI4;
+ props[1].ulVal = numThreads;
{
CMyComPtr<ICompressSetCoderProperties> setCoderProperties;
RINOK(encoder.QueryInterface(IID_ICompressSetCoderProperties, &setCoderProperties));
if (!setCoderProperties)
return E_FAIL;
- RINOK(setCoderProperties->SetCoderProperties(propIDs, properties, kNumProps));
+ RINOK(setCoderProperties->SetCoderProperties(propIDs, props, kNumProps));
CMyComPtr<ICompressWriteCoderProperties> writeCoderProperties;
encoder.QueryInterface(IID_ICompressWriteCoderProperties, &writeCoderProperties);
diff --git a/CPP/7zip/Compress/LZMA_Alone/makefile b/CPP/7zip/Compress/LZMA_Alone/makefile
index 1c4baa0b..f6d94081 100755
--- a/CPP/7zip/Compress/LZMA_Alone/makefile
+++ b/CPP/7zip/Compress/LZMA_Alone/makefile
@@ -26,6 +26,7 @@ WIN_OBJS = \
$O\System.obj
7ZIP_COMMON_OBJS = \
+ $O\CWrappers.obj \
$O\InBuffer.obj \
$O\OutBuffer.obj \
$O\StreamUtils.obj \
diff --git a/CPP/7zip/Compress/Lzma2Decoder.cpp b/CPP/7zip/Compress/Lzma2Decoder.cpp
new file mode 100755
index 00000000..322015e2
--- /dev/null
+++ b/CPP/7zip/Compress/Lzma2Decoder.cpp
@@ -0,0 +1,189 @@
+// Lzma2Decoder.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/Alloc.h"
+
+#include "../Common/StreamUtils.h"
+
+#include "Lzma2Decoder.h"
+
+static HRESULT SResToHRESULT(SRes res)
+{
+ switch(res)
+ {
+ case SZ_OK: return S_OK;
+ case SZ_ERROR_MEM: return E_OUTOFMEMORY;
+ case SZ_ERROR_PARAM: return E_INVALIDARG;
+ // case SZ_ERROR_PROGRESS: return E_ABORT;
+ case SZ_ERROR_DATA: return S_FALSE;
+ }
+ return E_FAIL;
+}
+
+namespace NCompress {
+namespace NLzma2 {
+
+static const UInt32 kInBufSize = 1 << 20;
+
+CDecoder::CDecoder(): _inBuf(0), _outSizeDefined(false)
+{
+ Lzma2Dec_Construct(&_state);
+}
+
+static void *SzAlloc(void *p, size_t size) { p = p; return MyAlloc(size); }
+static void SzFree(void *p, void *address) { p = p; MyFree(address); }
+static ISzAlloc g_Alloc = { SzAlloc, SzFree };
+
+CDecoder::~CDecoder()
+{
+ Lzma2Dec_Free(&_state, &g_Alloc);
+ MyFree(_inBuf);
+}
+
+STDMETHODIMP CDecoder::SetDecoderProperties2(const Byte *prop, UInt32 size)
+{
+ if (size != 1) return SZ_ERROR_UNSUPPORTED;
+ RINOK(SResToHRESULT(Lzma2Dec_Allocate(&_state, prop[0], &g_Alloc)));
+ if (_inBuf == 0)
+ {
+ _inBuf = (Byte *)MyAlloc(kInBufSize);
+ if (_inBuf == 0)
+ return E_OUTOFMEMORY;
+ }
+
+ return S_OK;
+}
+
+STDMETHODIMP CDecoder::GetInStreamProcessedSize(UInt64 *value) { *value = _inSizeProcessed; return S_OK; }
+STDMETHODIMP CDecoder::SetInStream(ISequentialInStream *inStream) { _inStream = inStream; return S_OK; }
+STDMETHODIMP CDecoder::ReleaseInStream() { _inStream.Release(); return S_OK; }
+
+STDMETHODIMP CDecoder::SetOutStreamSize(const UInt64 *outSize)
+{
+ _outSizeDefined = (outSize != NULL);
+ if (_outSizeDefined)
+ _outSize = *outSize;
+
+ Lzma2Dec_Init(&_state);
+
+ _inPos = _inSize = 0;
+ _inSizeProcessed = _outSizeProcessed = 0;
+ return S_OK;
+}
+
+STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream,
+ ISequentialOutStream *outStream, const UInt64 * /* inSize */,
+ const UInt64 *outSize, ICompressProgressInfo *progress)
+{
+ if (_inBuf == 0)
+ return S_FALSE;
+ SetOutStreamSize(outSize);
+
+ for (;;)
+ {
+ if (_inPos == _inSize)
+ {
+ _inPos = _inSize = 0;
+ RINOK(inStream->Read(_inBuf, kInBufSize, &_inSize));
+ }
+
+ SizeT dicPos = _state.decoder.dicPos;
+ SizeT curSize = _state.decoder.dicBufSize - dicPos;
+ const UInt32 kStepSize = ((UInt32)1 << 22);
+ if (curSize > kStepSize)
+ curSize = (SizeT)kStepSize;
+
+ ELzmaFinishMode finishMode = LZMA_FINISH_ANY;
+ if (_outSizeDefined)
+ {
+ const UInt64 rem = _outSize - _outSizeProcessed;
+ if (rem < curSize)
+ {
+ curSize = (SizeT)rem;
+ /*
+ // finishMode = LZMA_FINISH_END;
+ we can't use LZMA_FINISH_END here to allow partial decoding
+ */
+ }
+ }
+
+ SizeT inSizeProcessed = _inSize - _inPos;
+ ELzmaStatus status;
+ SRes res = Lzma2Dec_DecodeToDic(&_state, dicPos + curSize, _inBuf + _inPos, &inSizeProcessed, finishMode, &status);
+
+ _inPos += (UInt32)inSizeProcessed;
+ _inSizeProcessed += inSizeProcessed;
+ SizeT outSizeProcessed = _state.decoder.dicPos - dicPos;
+ _outSizeProcessed += outSizeProcessed;
+
+ bool finished = (inSizeProcessed == 0 && outSizeProcessed == 0);
+ bool stopDecoding = (_outSizeDefined && _outSizeProcessed >= _outSize);
+
+ if (res != 0 || _state.decoder.dicPos == _state.decoder.dicBufSize || finished || stopDecoding)
+ {
+ HRESULT res2 = WriteStream(outStream, _state.decoder.dic, _state.decoder.dicPos);
+ if (res != 0)
+ return S_FALSE;
+ RINOK(res2);
+ if (stopDecoding)
+ return S_OK;
+ if (finished)
+ return (status == LZMA_STATUS_FINISHED_WITH_MARK ? S_OK : S_FALSE);
+ }
+ if (_state.decoder.dicPos == _state.decoder.dicBufSize)
+ _state.decoder.dicPos = 0;
+
+ if (progress != NULL)
+ {
+ RINOK(progress->SetRatioInfo(&_inSizeProcessed, &_outSizeProcessed));
+ }
+ }
+}
+
+#ifndef NO_READ_FROM_CODER
+
+STDMETHODIMP CDecoder::Read(void *data, UInt32 size, UInt32 *processedSize)
+{
+ if (processedSize)
+ *processedSize = 0;
+ do
+ {
+ if (_inPos == _inSize)
+ {
+ _inPos = _inSize = 0;
+ RINOK(_inStream->Read(_inBuf, kInBufSize, &_inSize));
+ }
+ {
+ SizeT inProcessed = _inSize - _inPos;
+
+ if (_outSizeDefined)
+ {
+ const UInt64 rem = _outSize - _outSizeProcessed;
+ if (rem < size)
+ size = (UInt32)rem;
+ }
+
+ SizeT outProcessed = size;
+ ELzmaStatus status;
+ SRes res = Lzma2Dec_DecodeToBuf(&_state, (Byte *)data, &outProcessed,
+ _inBuf + _inPos, &inProcessed, LZMA_FINISH_ANY, &status);
+ _inPos += (UInt32)inProcessed;
+ _inSizeProcessed += inProcessed;
+ _outSizeProcessed += outProcessed;
+ size -= (UInt32)outProcessed;
+ data = (Byte *)data + outProcessed;
+ if (processedSize)
+ *processedSize += (UInt32)outProcessed;
+ RINOK(SResToHRESULT(res));
+ if (inProcessed == 0 && outProcessed == 0)
+ return S_OK;
+ }
+ }
+ while (size != 0);
+ return S_OK;
+}
+
+#endif
+
+}}
diff --git a/CPP/7zip/Compress/Lzma2Decoder.h b/CPP/7zip/Compress/Lzma2Decoder.h
new file mode 100755
index 00000000..fd7ca2f3
--- /dev/null
+++ b/CPP/7zip/Compress/Lzma2Decoder.h
@@ -0,0 +1,73 @@
+// Lzma2Decoder.h
+
+#ifndef __LZMA2_DECODER_H
+#define __LZMA2_DECODER_H
+
+#include "../../../C/Lzma2Dec.h"
+
+#include "../../Common/MyCom.h"
+
+#include "../ICoder.h"
+
+namespace NCompress {
+namespace NLzma2 {
+
+class CDecoder:
+ public ICompressCoder,
+ public ICompressSetDecoderProperties2,
+ public ICompressGetInStreamProcessedSize,
+ #ifndef NO_READ_FROM_CODER
+ public ICompressSetInStream,
+ public ICompressSetOutStreamSize,
+ public ISequentialInStream,
+ #endif
+ public CMyUnknownImp
+{
+ CMyComPtr<ISequentialInStream> _inStream;
+ Byte *_inBuf;
+ UInt32 _inPos;
+ UInt32 _inSize;
+ CLzma2Dec _state;
+ bool _outSizeDefined;
+ UInt64 _outSize;
+ UInt64 _inSizeProcessed;
+ UInt64 _outSizeProcessed;
+public:
+
+ #ifndef NO_READ_FROM_CODER
+ MY_UNKNOWN_IMP5(
+ ICompressSetDecoderProperties2,
+ ICompressGetInStreamProcessedSize,
+ ICompressSetInStream,
+ ICompressSetOutStreamSize,
+ ISequentialInStream)
+ #else
+ MY_UNKNOWN_IMP2(
+ ICompressSetDecoderProperties2,
+ ICompressGetInStreamProcessedSize)
+ #endif
+
+ STDMETHOD(Code)(ISequentialInStream *inStream,
+ ISequentialOutStream *outStream, const UInt64 *_inSize, const UInt64 *outSize,
+ ICompressProgressInfo *progress);
+
+ STDMETHOD(SetDecoderProperties2)(const Byte *data, UInt32 size);
+
+ STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
+
+ STDMETHOD(SetInStream)(ISequentialInStream *inStream);
+ STDMETHOD(ReleaseInStream)();
+ STDMETHOD(SetOutStreamSize)(const UInt64 *outSize);
+
+ #ifndef NO_READ_FROM_CODER
+ STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+ #endif
+
+ CDecoder();
+ virtual ~CDecoder();
+
+};
+
+}}
+
+#endif
diff --git a/CPP/7zip/Compress/Lzma2Encoder.cpp b/CPP/7zip/Compress/Lzma2Encoder.cpp
new file mode 100755
index 00000000..5e4c71be
--- /dev/null
+++ b/CPP/7zip/Compress/Lzma2Encoder.cpp
@@ -0,0 +1,94 @@
+// Lzma2Encoder.cpp
+
+#include "StdAfx.h"
+
+#include "../../../C/Alloc.h"
+
+#include "../Common/CWrappers.h"
+#include "../Common/StreamUtils.h"
+
+#include "Lzma2Encoder.h"
+
+namespace NCompress {
+
+namespace NLzma {
+
+HRESULT SetLzmaProp(PROPID propID, const PROPVARIANT &prop, CLzmaEncProps &ep);
+
+}
+
+namespace NLzma2 {
+
+static void *SzBigAlloc(void *, size_t size) { return BigAlloc(size); }
+static void SzBigFree(void *, void *address) { BigFree(address); }
+static ISzAlloc g_BigAlloc = { SzBigAlloc, SzBigFree };
+
+static void *SzAlloc(void *, size_t size) { return MyAlloc(size); }
+static void SzFree(void *, void *address) { MyFree(address); }
+static ISzAlloc g_Alloc = { SzAlloc, SzFree };
+
+CEncoder::CEncoder()
+{
+ _encoder = 0;
+ _encoder = Lzma2Enc_Create(&g_Alloc, &g_BigAlloc);
+ if (_encoder == 0)
+ throw 1;
+}
+
+CEncoder::~CEncoder()
+{
+ if (_encoder != 0)
+ Lzma2Enc_Destroy(_encoder);
+}
+
+HRESULT SetLzma2Prop(PROPID propID, const PROPVARIANT &prop, CLzma2EncProps &lzma2Props)
+{
+ switch (propID)
+ {
+ case NCoderPropID::kBlockSize:
+ if (prop.vt != VT_UI4) return E_INVALIDARG; lzma2Props.blockSize = prop.ulVal; break;
+ case NCoderPropID::kNumThreads:
+ if (prop.vt != VT_UI4) return E_INVALIDARG; lzma2Props.numTotalThreads = (int)(prop.ulVal); break;
+ default:
+ RINOK(NLzma::SetLzmaProp(propID, prop, lzma2Props.lzmaProps));
+ }
+ return S_OK;
+}
+
+STDMETHODIMP CEncoder::SetCoderProperties(const PROPID *propIDs,
+ const PROPVARIANT *coderProps, UInt32 numProps)
+{
+ CLzma2EncProps lzma2Props;
+ Lzma2EncProps_Init(&lzma2Props);
+
+ for (UInt32 i = 0; i < numProps; i++)
+ {
+ RINOK(SetLzma2Prop(propIDs[i], coderProps[i], lzma2Props));
+ }
+ return SResToHRESULT(Lzma2Enc_SetProps(_encoder, &lzma2Props));
+}
+
+STDMETHODIMP CEncoder::WriteCoderProperties(ISequentialOutStream *outStream)
+{
+ Byte prop = Lzma2Enc_WriteProperties(_encoder);
+ return WriteStream(outStream, &prop, 1);
+}
+
+STDMETHODIMP CEncoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgressInfo *progress)
+{
+ CSeqInStreamWrap inWrap(inStream);
+ CSeqOutStreamWrap outWrap(outStream);
+ CCompressProgressWrap progressWrap(progress);
+
+ SRes res = Lzma2Enc_Encode(_encoder, &outWrap.p, &inWrap.p, progress ? &progressWrap.p : NULL);
+ if (res == SZ_ERROR_READ && inWrap.Res != S_OK)
+ return inWrap.Res;
+ if (res == SZ_ERROR_WRITE && outWrap.Res != S_OK)
+ return outWrap.Res;
+ if (res == SZ_ERROR_PROGRESS && progressWrap.Res != S_OK)
+ return progressWrap.Res;
+ return SResToHRESULT(res);
+}
+
+}}
diff --git a/CPP/7zip/Compress/Lzma2Encoder.h b/CPP/7zip/Compress/Lzma2Encoder.h
new file mode 100755
index 00000000..f0fb74d3
--- /dev/null
+++ b/CPP/7zip/Compress/Lzma2Encoder.h
@@ -0,0 +1,36 @@
+// Lzma2Encoder.h
+
+#ifndef __LZMA2_ENCODER_H
+#define __LZMA2_ENCODER_H
+
+#include "../../../C/Lzma2Enc.h"
+
+#include "../../Common/MyCom.h"
+
+#include "../ICoder.h"
+
+namespace NCompress {
+namespace NLzma2 {
+
+class CEncoder:
+ public ICompressCoder,
+ public ICompressSetCoderProperties,
+ public ICompressWriteCoderProperties,
+ public CMyUnknownImp
+{
+ CLzma2EncHandle _encoder;
+public:
+ MY_UNKNOWN_IMP2(ICompressSetCoderProperties, ICompressWriteCoderProperties)
+
+ STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
+ STDMETHOD(SetCoderProperties)(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps);
+ STDMETHOD(WriteCoderProperties)(ISequentialOutStream *outStream);
+
+ CEncoder();
+ virtual ~CEncoder();
+};
+
+}}
+
+#endif
diff --git a/CPP/7zip/Compress/Lzma2Register.cpp b/CPP/7zip/Compress/Lzma2Register.cpp
new file mode 100755
index 00000000..cace871e
--- /dev/null
+++ b/CPP/7zip/Compress/Lzma2Register.cpp
@@ -0,0 +1,20 @@
+// Lzma2Register.cpp
+
+#include "StdAfx.h"
+
+#include "../Common/RegisterCodec.h"
+
+#include "Lzma2Decoder.h"
+
+static void *CreateCodec() { return (void *)(ICompressCoder *)(new NCompress::NLzma2::CDecoder); }
+#ifndef EXTRACT_ONLY
+#include "Lzma2Encoder.h"
+static void *CreateCodecOut() { return (void *)(ICompressCoder *)(new NCompress::NLzma2::CEncoder); }
+#else
+#define CreateCodecOut 0
+#endif
+
+static CCodecInfo g_CodecInfo =
+ { CreateCodec, CreateCodecOut, 0x21, L"LZMA2", 1, false };
+
+REGISTER_CODEC(LZMA2)
diff --git a/CPP/7zip/Compress/LzmaDecoder.cpp b/CPP/7zip/Compress/LzmaDecoder.cpp
index 5bfffe90..c74d5ade 100755
--- a/CPP/7zip/Compress/LzmaDecoder.cpp
+++ b/CPP/7zip/Compress/LzmaDecoder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "../Common/StreamUtils.h"
@@ -19,7 +16,6 @@ static HRESULT SResToHRESULT(SRes res)
case SZ_ERROR_MEM: return E_OUTOFMEMORY;
case SZ_ERROR_PARAM: return E_INVALIDARG;
case SZ_ERROR_UNSUPPORTED: return E_NOTIMPL;
- // case SZ_ERROR_PROGRESS: return E_ABORT;
case SZ_ERROR_DATA: return S_FALSE;
}
return E_FAIL;
@@ -30,8 +26,10 @@ namespace NLzma {
static const UInt32 kInBufSize = 1 << 20;
-CDecoder::CDecoder(): _inBuf(0), _outSizeDefined(false), FinishStream(false)
+CDecoder::CDecoder(): _inBuf(0), _propsWereSet(false), _outSizeDefined(false), FinishStream(false)
{
+ _inSizeProcessed = 0;
+ _inPos = _inSize = 0;
LzmaDec_Construct(&_state);
}
@@ -45,43 +43,47 @@ CDecoder::~CDecoder()
MyFree(_inBuf);
}
-STDMETHODIMP CDecoder::SetDecoderProperties2(const Byte *prop, UInt32 size)
+HRESULT CDecoder::CreateInputBuffer()
{
- RINOK(SResToHRESULT(LzmaDec_Allocate(&_state, prop, size, &g_Alloc)));
-
if (_inBuf == 0)
{
_inBuf = (Byte *)MyAlloc(kInBufSize);
if (_inBuf == 0)
return E_OUTOFMEMORY;
}
-
return S_OK;
}
-STDMETHODIMP CDecoder::GetInStreamProcessedSize(UInt64 *value) { *value = _inSizeProcessed; return S_OK; }
-STDMETHODIMP CDecoder::SetInStream(ISequentialInStream *inStream) { _inStream = inStream; return S_OK; }
-STDMETHODIMP CDecoder::ReleaseInStream() { _inStream.Release(); return S_OK; }
+STDMETHODIMP CDecoder::SetDecoderProperties2(const Byte *prop, UInt32 size)
+{
+ RINOK(SResToHRESULT(LzmaDec_Allocate(&_state, prop, size, &g_Alloc)));
+ _propsWereSet = true;
+ return CreateInputBuffer();
+}
-STDMETHODIMP CDecoder::SetOutStreamSize(const UInt64 *outSize)
+void CDecoder::SetOutStreamSizeResume(const UInt64 *outSize)
{
_outSizeDefined = (outSize != NULL);
if (_outSizeDefined)
_outSize = *outSize;
-
+ _outSizeProcessed = 0;
LzmaDec_Init(&_state);
-
+}
+
+STDMETHODIMP CDecoder::SetOutStreamSize(const UInt64 *outSize)
+{
+ _inSizeProcessed = 0;
_inPos = _inSize = 0;
- _inSizeProcessed = _outSizeProcessed = 0;
+ SetOutStreamSizeResume(outSize);
return S_OK;
}
-STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
- const UInt64 * /* inSize */, const UInt64 *outSize, ICompressProgressInfo *progress)
+HRESULT CDecoder::CodeSpec(ISequentialInStream *inStream, ISequentialOutStream *outStream, ICompressProgressInfo *progress)
{
- if (_inBuf == 0)
+ if (_inBuf == 0 || !_propsWereSet)
return S_FALSE;
- SetOutStreamSize(outSize);
+
+ UInt64 startInProgress = _inSizeProcessed;
for (;;)
{
@@ -135,15 +137,26 @@ STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream, ISequentialOutStream
if (_state.dicPos == _state.dicBufSize)
_state.dicPos = 0;
- if (progress != NULL)
+ if (progress)
{
- RINOK(progress->SetRatioInfo(&_inSizeProcessed, &_outSizeProcessed));
+ UInt64 inSize = _inSizeProcessed - startInProgress;
+ RINOK(progress->SetRatioInfo(&inSize, &_outSizeProcessed));
}
}
}
+STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ const UInt64 * /* inSize */, const UInt64 *outSize, ICompressProgressInfo *progress)
+{
+ SetOutStreamSize(outSize);
+ return CodeSpec(inStream, outStream, progress);
+}
+
#ifndef NO_READ_FROM_CODER
+STDMETHODIMP CDecoder::SetInStream(ISequentialInStream *inStream) { _inStream = inStream; return S_OK; }
+STDMETHODIMP CDecoder::ReleaseInStream() { _inStream.Release(); return S_OK; }
+
STDMETHODIMP CDecoder::Read(void *data, UInt32 size, UInt32 *processedSize)
{
if (processedSize)
@@ -185,6 +198,42 @@ STDMETHODIMP CDecoder::Read(void *data, UInt32 size, UInt32 *processedSize)
return S_OK;
}
+HRESULT CDecoder::CodeResume(ISequentialOutStream *outStream, const UInt64 *outSize, ICompressProgressInfo *progress)
+{
+ SetOutStreamSizeResume(outSize);
+ return CodeSpec(_inStream, outStream, progress);
+}
+
+HRESULT CDecoder::ReadFromInputStream(void *data, UInt32 size, UInt32 *processedSize)
+{
+ RINOK(CreateInputBuffer());
+ if (processedSize)
+ *processedSize = 0;
+ while (size > 0)
+ {
+ if (_inPos == _inSize)
+ {
+ _inPos = _inSize = 0;
+ RINOK(_inStream->Read(_inBuf, kInBufSize, &_inSize));
+ if (_inSize == 0)
+ break;
+ }
+ {
+ UInt32 curSize = _inSize - _inPos;
+ if (curSize > size)
+ curSize = size;
+ memcpy(data, _inBuf + _inPos, curSize);
+ _inPos += curSize;
+ _inSizeProcessed += curSize;
+ size -= curSize;
+ data = (Byte *)data + curSize;
+ if (processedSize)
+ *processedSize += curSize;
+ }
+ }
+ return S_OK;
+}
+
#endif
}}
diff --git a/CPP/7zip/Compress/LzmaDecoder.h b/CPP/7zip/Compress/LzmaDecoder.h
index e132d5cb..d4bc9d3b 100755
--- a/CPP/7zip/Compress/LzmaDecoder.h
+++ b/CPP/7zip/Compress/LzmaDecoder.h
@@ -3,10 +3,7 @@
#ifndef __LZMA_DECODER_H
#define __LZMA_DECODER_H
-extern "C"
-{
#include "../../../C/LzmaDec.h"
-}
#include "../../Common/MyCom.h"
#include "../ICoder.h"
@@ -17,7 +14,6 @@ namespace NLzma {
class CDecoder:
public ICompressCoder,
public ICompressSetDecoderProperties2,
- public ICompressGetInStreamProcessedSize,
#ifndef NO_READ_FROM_CODER
public ICompressSetInStream,
public ICompressSetOutStreamSize,
@@ -30,35 +26,42 @@ class CDecoder:
UInt32 _inPos;
UInt32 _inSize;
CLzmaDec _state;
+ bool _propsWereSet;
bool _outSizeDefined;
UInt64 _outSize;
UInt64 _inSizeProcessed;
UInt64 _outSizeProcessed;
-public:
+
+ HRESULT CreateInputBuffer();
+ HRESULT CodeSpec(ISequentialInStream *inStream, ISequentialOutStream *outStream, ICompressProgressInfo *progress);
+ void SetOutStreamSizeResume(const UInt64 *outSize);
+public:
+ MY_QUERYINTERFACE_BEGIN
+ MY_QUERYINTERFACE_ENTRY(ICompressSetDecoderProperties2)
#ifndef NO_READ_FROM_CODER
- MY_UNKNOWN_IMP5(
- ICompressSetDecoderProperties2,
- ICompressGetInStreamProcessedSize,
- ICompressSetInStream,
- ICompressSetOutStreamSize,
- ISequentialInStream)
- #else
- MY_UNKNOWN_IMP2(
- ICompressSetDecoderProperties2,
- ICompressGetInStreamProcessedSize)
+ MY_QUERYINTERFACE_ENTRY(ICompressSetInStream)
+ MY_QUERYINTERFACE_ENTRY(ICompressSetOutStreamSize)
+ MY_QUERYINTERFACE_ENTRY(ISequentialInStream)
#endif
+ MY_QUERYINTERFACE_END
+ MY_ADDREF_RELEASE
STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
STDMETHOD(SetDecoderProperties2)(const Byte *data, UInt32 size);
- STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
- STDMETHOD(SetInStream)(ISequentialInStream *inStream);
- STDMETHOD(ReleaseInStream)();
STDMETHOD(SetOutStreamSize)(const UInt64 *outSize);
#ifndef NO_READ_FROM_CODER
+
+ STDMETHOD(SetInStream)(ISequentialInStream *inStream);
+ STDMETHOD(ReleaseInStream)();
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
+
+ HRESULT CodeResume(ISequentialOutStream *outStream, const UInt64 *outSize, ICompressProgressInfo *progress);
+ HRESULT ReadFromInputStream(void *data, UInt32 size, UInt32 *processedSize);
+ UInt64 GetInputProcessedSize() const { return _inSizeProcessed; }
+
#endif
bool FinishStream;
diff --git a/CPP/7zip/Compress/LzmaEncoder.cpp b/CPP/7zip/Compress/LzmaEncoder.cpp
index 986e1edb..9bdedaeb 100755
--- a/CPP/7zip/Compress/LzmaEncoder.cpp
+++ b/CPP/7zip/Compress/LzmaEncoder.cpp
@@ -2,49 +2,16 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
+#include "../Common/CWrappers.h"
#include "../Common/StreamUtils.h"
#include "LzmaEncoder.h"
-static HRESULT SResToHRESULT(SRes res)
-{
- switch(res)
- {
- case SZ_OK: return S_OK;
- case SZ_ERROR_MEM: return E_OUTOFMEMORY;
- case SZ_ERROR_PARAM: return E_INVALIDARG;
- // case SZ_ERROR_THREAD: return E_FAIL;
- }
- return E_FAIL;
-}
-
namespace NCompress {
namespace NLzma {
-static const UInt32 kStreamStepSize = (UInt32)1 << 31;
-
-static SRes MyRead(void *object, void *data, size_t *size)
-{
- UInt32 curSize = ((*size < kStreamStepSize) ? (UInt32)*size : kStreamStepSize);
- HRESULT res = ((CSeqInStream *)object)->RealStream->Read(data, curSize, &curSize);
- *size = curSize;
- return (SRes)res;
-}
-
-static size_t MyWrite(void *object, const void *data, size_t size)
-{
- CSeqOutStream *p = (CSeqOutStream *)object;
- p->Res = WriteStream(p->RealStream, data, size);
- if (p->Res != 0)
- return 0;
- return size;
-}
-
static void *SzBigAlloc(void *, size_t size) { return BigAlloc(size); }
static void SzBigFree(void *, void *address) { BigFree(address); }
static ISzAlloc g_BigAlloc = { SzBigAlloc, SzBigFree };
@@ -55,8 +22,6 @@ static ISzAlloc g_Alloc = { SzAlloc, SzFree };
CEncoder::CEncoder()
{
- _seqInStream.SeqInStream.Read = MyRead;
- _seqOutStream.SeqOutStream.Write = MyWrite;
_encoder = 0;
_encoder = LzmaEnc_Create(&g_Alloc);
if (_encoder == 0)
@@ -108,6 +73,31 @@ static int ParseMatchFinder(const wchar_t *s, int *btMode, int *numHashBytes)
return 1;
}
+HRESULT SetLzmaProp(PROPID propID, const PROPVARIANT &prop, CLzmaEncProps &ep)
+{
+ if (propID == NCoderPropID::kMatchFinder)
+ {
+ if (prop.vt != VT_BSTR)
+ return E_INVALIDARG;
+ return ParseMatchFinder(prop.bstrVal, &ep.btMode, &ep.numHashBytes) ? S_OK : E_INVALIDARG;
+ }
+ if (prop.vt != VT_UI4)
+ return E_INVALIDARG;
+ UInt32 v = prop.ulVal;
+ switch (propID)
+ {
+ case NCoderPropID::kNumFastBytes: ep.fb = v; break;
+ case NCoderPropID::kMatchFinderCycles: ep.mc = v; break;
+ case NCoderPropID::kAlgorithm: ep.algo = v; break;
+ case NCoderPropID::kDictionarySize: ep.dictSize = v; break;
+ case NCoderPropID::kPosStateBits: ep.pb = v; break;
+ case NCoderPropID::kLitPosBits: ep.lp = v; break;
+ case NCoderPropID::kLitContextBits: ep.lc = v; break;
+ default: return E_INVALIDARG;
+ }
+ return S_OK;
+}
+
STDMETHODIMP CEncoder::SetCoderProperties(const PROPID *propIDs,
const PROPVARIANT *coderProps, UInt32 numProps)
{
@@ -117,34 +107,15 @@ STDMETHODIMP CEncoder::SetCoderProperties(const PROPID *propIDs,
for (UInt32 i = 0; i < numProps; i++)
{
const PROPVARIANT &prop = coderProps[i];
- switch (propIDs[i])
+ PROPID propID = propIDs[i];
+ switch (propID)
{
- case NCoderPropID::kNumFastBytes:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.fb = prop.ulVal; break;
- case NCoderPropID::kMatchFinderCycles:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.mc = prop.ulVal; break;
- case NCoderPropID::kAlgorithm:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.algo = prop.ulVal; break;
- case NCoderPropID::kDictionarySize:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.dictSize = prop.ulVal; break;
- case NCoderPropID::kPosStateBits:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.pb = prop.ulVal; break;
- case NCoderPropID::kLitPosBits:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.lp = prop.ulVal; break;
- case NCoderPropID::kLitContextBits:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.lc = prop.ulVal; break;
- case NCoderPropID::kNumThreads:
- if (prop.vt != VT_UI4) return E_INVALIDARG; props.numThreads = prop.ulVal; break;
- case NCoderPropID::kMultiThread:
- if (prop.vt != VT_BOOL) return E_INVALIDARG; props.numThreads = ((prop.boolVal == VARIANT_TRUE) ? 2 : 1); break;
case NCoderPropID::kEndMarker:
if (prop.vt != VT_BOOL) return E_INVALIDARG; props.writeEndMark = (prop.boolVal == VARIANT_TRUE); break;
- case NCoderPropID::kMatchFinder:
- if (prop.vt != VT_BSTR) return E_INVALIDARG;
- if (!ParseMatchFinder(prop.bstrVal, &props.btMode, &props.numHashBytes /* , &_matchFinderBase.skipModeBits */))
- return E_INVALIDARG; break;
+ case NCoderPropID::kNumThreads:
+ if (prop.vt != VT_UI4) return E_INVALIDARG; props.numThreads = prop.ulVal; break;
default:
- return E_INVALIDARG;
+ RINOK(SetLzmaProp(propID, prop, props));
}
}
return SResToHRESULT(LzmaEnc_SetProps(_encoder, &props));
@@ -158,53 +129,20 @@ STDMETHODIMP CEncoder::WriteCoderProperties(ISequentialOutStream *outStream)
return WriteStream(outStream, props, size);
}
-STDMETHODIMP CEncoder::SetOutStream(ISequentialOutStream *outStream)
-{
- _seqOutStream.RealStream = outStream;
- _seqOutStream.Res = S_OK;
- return S_OK;
-}
-
-STDMETHODIMP CEncoder::ReleaseOutStream()
-{
- _seqOutStream.RealStream.Release();
- return S_OK;
-}
-
-typedef struct _CCompressProgressImp
-{
- ICompressProgress p;
- ICompressProgressInfo *Progress;
- HRESULT Res;
-} CCompressProgressImp;
-
-#define PROGRESS_UNKNOWN_VALUE ((UInt64)(Int64)-1)
-
-#define CONVERT_PR_VAL(x) (x == PROGRESS_UNKNOWN_VALUE ? NULL : &x)
-
-SRes CompressProgress(void *pp, UInt64 inSize, UInt64 outSize)
-{
- CCompressProgressImp *p = (CCompressProgressImp *)pp;
- p->Res = p->Progress->SetRatioInfo(CONVERT_PR_VAL(inSize), CONVERT_PR_VAL(outSize));
- return (SRes)p->Res;
-}
-
STDMETHODIMP CEncoder::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgressInfo *progress)
{
- CCompressProgressImp progressImp;
- progressImp.p.Progress = CompressProgress;
- progressImp.Progress = progress;
- progressImp.Res = SZ_OK;
-
- _seqInStream.RealStream = inStream;
- SetOutStream(outStream);
- SRes res = LzmaEnc_Encode(_encoder, &_seqOutStream.SeqOutStream, &_seqInStream.SeqInStream, progress ? &progressImp.p : NULL, &g_Alloc, &g_BigAlloc);
- ReleaseOutStream();
- if (res == SZ_ERROR_WRITE && _seqOutStream.Res != S_OK)
- return _seqOutStream.Res;
- if (res == SZ_ERROR_PROGRESS && progressImp.Res != S_OK)
- return progressImp.Res;
+ CSeqInStreamWrap inWrap(inStream);
+ CSeqOutStreamWrap outWrap(outStream);
+ CCompressProgressWrap progressWrap(progress);
+
+ SRes res = LzmaEnc_Encode(_encoder, &outWrap.p, &inWrap.p, progress ? &progressWrap.p : NULL, &g_Alloc, &g_BigAlloc);
+ if (res == SZ_ERROR_READ && inWrap.Res != S_OK)
+ return inWrap.Res;
+ if (res == SZ_ERROR_WRITE && outWrap.Res != S_OK)
+ return outWrap.Res;
+ if (res == SZ_ERROR_PROGRESS && progressWrap.Res != S_OK)
+ return progressWrap.Res;
return SResToHRESULT(res);
}
diff --git a/CPP/7zip/Compress/LzmaEncoder.h b/CPP/7zip/Compress/LzmaEncoder.h
index 4205d2b1..904c0002 100755
--- a/CPP/7zip/Compress/LzmaEncoder.h
+++ b/CPP/7zip/Compress/LzmaEncoder.h
@@ -3,10 +3,7 @@
#ifndef __LZMA_ENCODER_H
#define __LZMA_ENCODER_H
-extern "C"
-{
#include "../../../C/LzmaEnc.h"
-}
#include "../../Common/MyCom.h"
@@ -15,47 +12,22 @@ extern "C"
namespace NCompress {
namespace NLzma {
-struct CSeqInStream
-{
- ISeqInStream SeqInStream;
- ISequentialInStream *RealStream;
-};
-
-struct CSeqOutStream
-{
- ISeqOutStream SeqOutStream;
- CMyComPtr<ISequentialOutStream> RealStream;
- HRESULT Res;
-};
-
-class CEncoder :
+class CEncoder:
public ICompressCoder,
- public ICompressSetOutStream,
public ICompressSetCoderProperties,
public ICompressWriteCoderProperties,
public CMyUnknownImp
{
CLzmaEncHandle _encoder;
-
- CSeqInStream _seqInStream;
- CSeqOutStream _seqOutStream;
-
public:
- CEncoder();
-
- MY_UNKNOWN_IMP3(
- ICompressSetOutStream,
- ICompressSetCoderProperties,
- ICompressWriteCoderProperties
- )
+ MY_UNKNOWN_IMP2(ICompressSetCoderProperties, ICompressWriteCoderProperties)
STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
STDMETHOD(SetCoderProperties)(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps);
STDMETHOD(WriteCoderProperties)(ISequentialOutStream *outStream);
- STDMETHOD(SetOutStream)(ISequentialOutStream *outStream);
- STDMETHOD(ReleaseOutStream)();
+ CEncoder();
virtual ~CEncoder();
};
diff --git a/CPP/7zip/Compress/PpmdContext.h b/CPP/7zip/Compress/PpmdContext.h
index f4fa78e4..cfff53ed 100755
--- a/CPP/7zip/Compress/PpmdContext.h
+++ b/CPP/7zip/Compress/PpmdContext.h
@@ -1,5 +1,6 @@
// PpmdContext.h
-// This code is based on Dmitry Shkarin's PPMdH code
+// 2009-05-30 : Igor Pavlov : Public domain
+// This code is based on Dmitry Shkarin's PPMdH code (public domain)
#ifndef __COMPRESS_PPMD_CONTEXT_H
#define __COMPRESS_PPMD_CONTEXT_H
diff --git a/CPP/7zip/Compress/PpmdDecode.h b/CPP/7zip/Compress/PpmdDecode.h
index 860c65b4..d5ca25fe 100755
--- a/CPP/7zip/Compress/PpmdDecode.h
+++ b/CPP/7zip/Compress/PpmdDecode.h
@@ -1,5 +1,6 @@
// PpmdDecode.h
-// This code is based on Dmitry Shkarin's PPMdH code
+// 2009-05-30 : Igor Pavlov : Public domain
+// This code is based on Dmitry Shkarin's PPMdH code (public domain)
#ifndef __COMPRESS_PPMD_DECODE_H
#define __COMPRESS_PPMD_DECODE_H
diff --git a/CPP/7zip/Compress/PpmdDecoder.cpp b/CPP/7zip/Compress/PpmdDecoder.cpp
index dea36d9a..0ac98c8b 100755
--- a/CPP/7zip/Compress/PpmdDecoder.cpp
+++ b/CPP/7zip/Compress/PpmdDecoder.cpp
@@ -1,4 +1,5 @@
// PpmdDecoder.cpp
+// 2009-05-30 : Igor Pavlov : Public domain
#include "StdAfx.h"
diff --git a/CPP/7zip/Compress/PpmdDecoder.h b/CPP/7zip/Compress/PpmdDecoder.h
index 0d8817d4..31ab8f82 100755
--- a/CPP/7zip/Compress/PpmdDecoder.h
+++ b/CPP/7zip/Compress/PpmdDecoder.h
@@ -1,4 +1,5 @@
// PpmdDecoder.h
+// 2009-05-30 : Igor Pavlov : Public domain
#ifndef __COMPRESS_PPMD_DECODER_H
#define __COMPRESS_PPMD_DECODER_H
diff --git a/CPP/7zip/Compress/PpmdEncode.h b/CPP/7zip/Compress/PpmdEncode.h
index 0db92361..012f859c 100755
--- a/CPP/7zip/Compress/PpmdEncode.h
+++ b/CPP/7zip/Compress/PpmdEncode.h
@@ -1,5 +1,6 @@
// PpmdEncode.h
-// This code is based on Dmitry Shkarin's PPMdH code
+// 2009-05-30 : Igor Pavlov : Public domain
+// This code is based on Dmitry Shkarin's PPMdH code (public domain)
#ifndef __COMPRESS_PPMD_ENCODE_H
#define __COMPRESS_PPMD_ENCODE_H
diff --git a/CPP/7zip/Compress/PpmdEncoder.cpp b/CPP/7zip/Compress/PpmdEncoder.cpp
index 1e98c091..0af2ae7d 100755
--- a/CPP/7zip/Compress/PpmdEncoder.cpp
+++ b/CPP/7zip/Compress/PpmdEncoder.cpp
@@ -1,4 +1,5 @@
// PpmdEncoder.cpp
+// 2009-05-30 : Igor Pavlov : Public domain
#include "StdAfx.h"
diff --git a/CPP/7zip/Compress/PpmdEncoder.h b/CPP/7zip/Compress/PpmdEncoder.h
index 72b10651..07b368a7 100755
--- a/CPP/7zip/Compress/PpmdEncoder.h
+++ b/CPP/7zip/Compress/PpmdEncoder.h
@@ -1,4 +1,5 @@
// PpmdEncoder.h
+// 2009-05-30 : Igor Pavlov : Public domain
#ifndef __COMPRESS_PPMD_ENCODER_H
#define __COMPRESS_PPMD_ENCODER_H
diff --git a/CPP/7zip/Compress/PpmdRegister.cpp b/CPP/7zip/Compress/PpmdRegister.cpp
index cac1fb85..9f59fcdd 100755
--- a/CPP/7zip/Compress/PpmdRegister.cpp
+++ b/CPP/7zip/Compress/PpmdRegister.cpp
@@ -1,4 +1,5 @@
// PpmdRegister.cpp
+// 2009-05-30 : Igor Pavlov : Public domain
#include "StdAfx.h"
diff --git a/CPP/7zip/Compress/PpmdSubAlloc.h b/CPP/7zip/Compress/PpmdSubAlloc.h
index a7dd122c..143f4632 100755
--- a/CPP/7zip/Compress/PpmdSubAlloc.h
+++ b/CPP/7zip/Compress/PpmdSubAlloc.h
@@ -1,13 +1,11 @@
// PpmdSubAlloc.h
-// This code is based on Dmitry Shkarin's PPMdH code
+// 2009-05-30 : Igor Pavlov : Public domain
+// This code is based on Dmitry Shkarin's PPMdH code (public domain)
#ifndef __COMPRESS_PPMD_SUB_ALLOC_H
#define __COMPRESS_PPMD_SUB_ALLOC_H
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "PpmdType.h"
diff --git a/CPP/7zip/Compress/PpmdType.h b/CPP/7zip/Compress/PpmdType.h
index 4f0e65e8..e4b0203c 100755
--- a/CPP/7zip/Compress/PpmdType.h
+++ b/CPP/7zip/Compress/PpmdType.h
@@ -1,12 +1,6 @@
-/****************************************************************************
- * This file is part of PPMd project *
- * Written and distributed to public domain by Dmitry Shkarin 1997, *
- * 1999-2001 *
- * Contents: compilation parameters and miscelaneous definitions *
- * Comments: system & compiler dependent file
-
- * modified by Igor Pavlov (2004-08-29).
- ****************************************************************************/
+// PpmdType.h
+// 2009-05-30 : Igor Pavlov : Public domain
+// This code is based on Dmitry Shkarin's PPMdH code (public domain)
#ifndef __COMPRESS_PPMD_TYPE_H
#define __COMPRESS_PPMD_TYPE_H
diff --git a/CPP/7zip/Compress/RangeCoder.h b/CPP/7zip/Compress/RangeCoder.h
index 1e14ac1f..1eb2a6d4 100755
--- a/CPP/7zip/Compress/RangeCoder.h
+++ b/CPP/7zip/Compress/RangeCoder.h
@@ -1,4 +1,5 @@
// Compress/RangeCoder.h
+// 2009-05-30 : Igor Pavlov : Public domain
#ifndef __COMPRESS_RANGE_CODER_H
#define __COMPRESS_RANGE_CODER_H
diff --git a/CPP/7zip/Compress/RangeCoderBit.h b/CPP/7zip/Compress/RangeCoderBit.h
index 566cdd41..b5a1830d 100755
--- a/CPP/7zip/Compress/RangeCoderBit.h
+++ b/CPP/7zip/Compress/RangeCoderBit.h
@@ -1,4 +1,5 @@
// Compress/RangeCoderBit.h
+// 2009-05-30 : Igor Pavlov : Public domain
#ifndef __COMPRESS_RANGE_CODER_BIT_H
#define __COMPRESS_RANGE_CODER_BIT_H
diff --git a/CPP/7zip/Compress/Rar3Vm.cpp b/CPP/7zip/Compress/Rar3Vm.cpp
index ffca79d0..759dfbdb 100755
--- a/CPP/7zip/Compress/Rar3Vm.cpp
+++ b/CPP/7zip/Compress/Rar3Vm.cpp
@@ -12,11 +12,8 @@ Note:
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/7zCrc.h"
#include "../../../C/Alloc.h"
-}
#include "Rar3Vm.h"
diff --git a/CPP/7zip/Compress/ShrinkDecoder.cpp b/CPP/7zip/Compress/ShrinkDecoder.cpp
index 6eaacd4b..a89d323c 100755
--- a/CPP/7zip/Compress/ShrinkDecoder.cpp
+++ b/CPP/7zip/Compress/ShrinkDecoder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "../Common/InBuffer.h"
#include "../Common/OutBuffer.h"
diff --git a/CPP/7zip/Compress/ZDecoder.cpp b/CPP/7zip/Compress/ZDecoder.cpp
index 6982a7e0..e28c6451 100755
--- a/CPP/7zip/Compress/ZDecoder.cpp
+++ b/CPP/7zip/Compress/ZDecoder.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Alloc.h"
-}
#include "../Common/InBuffer.h"
#include "../Common/OutBuffer.h"
diff --git a/CPP/7zip/Crypto/7zAes.cpp b/CPP/7zip/Crypto/7zAes.cpp
index 3a1cbd68..41ccb1d2 100755
--- a/CPP/7zip/Crypto/7zAes.cpp
+++ b/CPP/7zip/Crypto/7zAes.cpp
@@ -2,14 +2,13 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/Sha256.h"
-}
#include "Windows/Synchronization.h"
+
#include "../Common/StreamObjects.h"
#include "../Common/StreamUtils.h"
+
#include "7zAes.h"
#include "MyAes.h"
diff --git a/CPP/7zip/Crypto/MyAes.h b/CPP/7zip/Crypto/MyAes.h
index ffc6fea5..24e90d6f 100755
--- a/CPP/7zip/Crypto/MyAes.h
+++ b/CPP/7zip/Crypto/MyAes.h
@@ -3,10 +3,7 @@
#ifndef __CRYPTO_MY_AES_H
#define __CRYPTO_MY_AES_H
-extern "C"
-{
#include "../../../C/Aes.h"
-}
#include "../../Common/MyCom.h"
#include "../../Common/Types.h"
diff --git a/CPP/7zip/Crypto/Rar20Crypto.cpp b/CPP/7zip/Crypto/Rar20Crypto.cpp
index 8fd2ab23..c2df0e52 100755
--- a/CPP/7zip/Crypto/Rar20Crypto.cpp
+++ b/CPP/7zip/Crypto/Rar20Crypto.cpp
@@ -2,12 +2,9 @@
#include "StdAfx.h"
-extern "C"
-{
- #include "../../../C/7zCrc.h"
- #include "../../../C/CpuArch.h"
- #include "../../../C/RotateDefs.h"
-}
+#include "../../../C/7zCrc.h"
+#include "../../../C/CpuArch.h"
+#include "../../../C/RotateDefs.h"
#include "Rar20Crypto.h"
diff --git a/CPP/7zip/Crypto/RarAes.h b/CPP/7zip/Crypto/RarAes.h
index aa8e06ba..374017b8 100755
--- a/CPP/7zip/Crypto/RarAes.h
+++ b/CPP/7zip/Crypto/RarAes.h
@@ -3,10 +3,7 @@
#ifndef __CRYPTO_RAR_AES_H
#define __CRYPTO_RAR_AES_H
-extern "C"
-{
#include "../../../C/Aes.h"
-}
#include "Common/Buffer.h"
#include "Common/MyCom.h"
diff --git a/CPP/7zip/Crypto/Sha1.cpp b/CPP/7zip/Crypto/Sha1.cpp
index af211f6c..84e589b2 100755
--- a/CPP/7zip/Crypto/Sha1.cpp
+++ b/CPP/7zip/Crypto/Sha1.cpp
@@ -4,11 +4,9 @@
#include "StdAfx.h"
-#include "Sha1.h"
-extern "C"
-{
#include "../../../C/RotateDefs.h"
-}
+
+#include "Sha1.h"
namespace NCrypto {
namespace NSha1 {
diff --git a/CPP/7zip/Crypto/WzAes.h b/CPP/7zip/Crypto/WzAes.h
index 2c7a4b43..22f4d4dd 100755
--- a/CPP/7zip/Crypto/WzAes.h
+++ b/CPP/7zip/Crypto/WzAes.h
@@ -12,10 +12,7 @@ specified in password Based File Encryption Utility:
#ifndef __CRYPTO_WZ_AES_H
#define __CRYPTO_WZ_AES_H
-extern "C"
-{
#include "../../../C/Aes.h"
-}
#include "Common/Buffer.h"
#include "Common/MyCom.h"
diff --git a/CPP/7zip/Crypto/ZipCrypto.cpp b/CPP/7zip/Crypto/ZipCrypto.cpp
index fc9f8ac2..f5972c57 100755
--- a/CPP/7zip/Crypto/ZipCrypto.cpp
+++ b/CPP/7zip/Crypto/ZipCrypto.cpp
@@ -2,10 +2,7 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/7zCrc.h"
-}
#include "../Common/StreamUtils.h"
diff --git a/CPP/7zip/Crypto/ZipStrong.cpp b/CPP/7zip/Crypto/ZipStrong.cpp
index e693febd..b29a3ad4 100755
--- a/CPP/7zip/Crypto/ZipStrong.cpp
+++ b/CPP/7zip/Crypto/ZipStrong.cpp
@@ -2,11 +2,8 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../../C/7zCrc.h"
#include "../../../C/CpuArch.h"
-}
#include "../Common/StreamUtils.h"
diff --git a/CPP/7zip/Guid.txt b/CPP/7zip/Guid.txt
index 387a74d7..25939aaa 100755
--- a/CPP/7zip/Guid.txt
+++ b/CPP/7zip/Guid.txt
@@ -7,11 +7,12 @@
01 IFolderArchive.h
05 IArchiveFolder
- 06 IInFolderArchive
+ // 06 IInFolderArchive // old
07 IFileExtractCallback.h::IFolderArchiveExtractCallback
0A IOutFolderArchive
0B IFolderArchiveUpdateCallback
0Ń Agent.h::IArchiveFolderInternal
+ 0D IInFolderArchive
03 IStream.h
@@ -65,6 +66,7 @@
40 IInArchiveGetStream
50 IArchiveOpenSetSubArchiveName
60 IInArchive
+ 61 IArchiveOpenSeq
80 IArchiveUpdateCallback
82 IArchiveUpdateCallback2
@@ -86,12 +88,15 @@
09 IFolderClone
0A IFolderSetFlatMode
0B IFolderOperationsExtractCallback
+ 0C IFolderArchiveProperties
+ 0D IGetFolderArchiveProperties
+ 0E IFolderProperties
-09 FolderInterface.h
+09 IFolder.h :: FOLDER_MANAGER_INTERFACE
- 00 // old IFolderManager
- 01 IFolderManager
+ 00 - 03 // old IFolderManager
+ 04 IFolderManager
@@ -116,8 +121,14 @@ Handler GUIDs:
07 7z
08 Cab
09 Nsis
- 0A Lzma
-
+ 0A lzma
+ 0B lzma86
+ 0C xz
+
+ D9 Ntfs
+ DA Fat
+ DB Mbr
+ DC Vhd
DD Pe
DE Elf
DF Mach-O
diff --git a/CPP/7zip/ICoder.h b/CPP/7zip/ICoder.h
index 262dfdba..b5d4d556 100755
--- a/CPP/7zip/ICoder.h
+++ b/CPP/7zip/ICoder.h
@@ -14,21 +14,15 @@ CODER_INTERFACE(ICompressProgressInfo, 0x04)
CODER_INTERFACE(ICompressCoder, 0x05)
{
- STDMETHOD(Code)(ISequentialInStream *inStream,
- ISequentialOutStream *outStream,
- const UInt64 *inSize,
- const UInt64 *outSize,
+ STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ const UInt64 *inSize, const UInt64 *outSize,
ICompressProgressInfo *progress) PURE;
};
CODER_INTERFACE(ICompressCoder2, 0x18)
{
- STDMETHOD(Code)(ISequentialInStream **inStreams,
- const UInt64 **inSizes,
- UInt32 numInStreams,
- ISequentialOutStream **outStreams,
- const UInt64 **outSizes,
- UInt32 numOutStreams,
+ STDMETHOD(Code)(ISequentialInStream **inStreams, const UInt64 **inSizes, UInt32 numInStreams,
+ ISequentialOutStream **outStreams, const UInt64 **outSizes, UInt32 numOutStreams,
ICompressProgressInfo *progress) PURE;
};
@@ -36,28 +30,27 @@ namespace NCoderPropID
{
enum EEnum
{
- kDictionarySize = 0x400,
+ kDefaultProp = 0,
+ kDictionarySize,
kUsedMemorySize,
kOrder,
kBlockSize,
- kPosStateBits = 0x440,
+ kPosStateBits,
kLitContextBits,
kLitPosBits,
- kNumFastBytes = 0x450,
+ kNumFastBytes,
kMatchFinder,
kMatchFinderCycles,
- kNumPasses = 0x460,
- kAlgorithm = 0x470,
- kMultiThread = 0x480,
+ kNumPasses,
+ kAlgorithm,
kNumThreads,
- kEndMarker = 0x490
+ kEndMarker
};
}
CODER_INTERFACE(ICompressSetCoderProperties, 0x20)
{
- STDMETHOD(SetCoderProperties)(const PROPID *propIDs,
- const PROPVARIANT *properties, UInt32 numProperties) PURE;
+ STDMETHOD(SetCoderProperties)(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps) PURE;
};
/*
@@ -74,7 +67,7 @@ CODER_INTERFACE(ICompressSetDecoderProperties2, 0x22)
CODER_INTERFACE(ICompressWriteCoderProperties, 0x23)
{
- STDMETHOD(WriteCoderProperties)(ISequentialOutStream *outStreams) PURE;
+ STDMETHOD(WriteCoderProperties)(ISequentialOutStream *outStream) PURE;
};
CODER_INTERFACE(ICompressGetInStreamProcessedSize, 0x24)
diff --git a/CPP/7zip/MyVersion.h b/CPP/7zip/MyVersion.h
index 68058ec3..ad2f0242 100755
--- a/CPP/7zip/MyVersion.h
+++ b/CPP/7zip/MyVersion.h
@@ -1,8 +1,8 @@
-#define MY_VER_MAJOR 4
-#define MY_VER_MINOR 65
+#define MY_VER_MAJOR 9
+#define MY_VER_MINOR 04
#define MY_VER_BUILD 0
-#define MY_VERSION "4.65"
-#define MY_7ZIP_VERSION "7-Zip 4.65"
-#define MY_DATE "2009-02-03"
+#define MY_VERSION "9.04 beta"
+#define MY_7ZIP_VERSION "7-Zip 9.04 beta"
+#define MY_DATE "2009-05-30"
#define MY_COPYRIGHT "Copyright (c) 1999-2009 Igor Pavlov"
#define MY_VERSION_COPYRIGHT_DATE MY_VERSION " " MY_COPYRIGHT " " MY_DATE
diff --git a/CPP/7zip/PropID.h b/CPP/7zip/PropID.h
index 9de487e8..d6f3a7c1 100755
--- a/CPP/7zip/PropID.h
+++ b/CPP/7zip/PropID.h
@@ -6,7 +6,7 @@
enum
{
kpidNoProperty = 0,
-
+ kpidMainSubfile = 1,
kpidHandlerItemIndex = 2,
kpidPath,
kpidName,
@@ -54,6 +54,12 @@ enum
kpidChecksum,
kpidCharacts,
kpidVa,
+ kpidId,
+ kpidShortName,
+ kpidCreatorApp,
+ kpidSectorSize,
+ kpidPosixAttrib,
+ kpidLink,
kpidTotalSize = 0x1100,
kpidFreeSpace,
diff --git a/CPP/7zip/UI/Agent/Agent.cpp b/CPP/7zip/UI/Agent/Agent.cpp
index 0b57049c..0b8f7c37 100755
--- a/CPP/7zip/UI/Agent/Agent.cpp
+++ b/CPP/7zip/UI/Agent/Agent.cpp
@@ -2,23 +2,14 @@
#include "StdAfx.h"
-#include "Common/StringConvert.h"
+#include "../../../../C/Sort.h"
+
#include "Common/ComTry.h"
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
-#include "Windows/FileFind.h"
-#include "../Common/DefaultName.h"
#include "../Common/ArchiveExtractCallback.h"
#include "Agent.h"
-extern "C"
-{
- #include "../../../../C/Sort.h"
-}
-
-
using namespace NWindows;
STDMETHODIMP CAgentFolder::GetAgentFolder(CAgentFolder **agentFolder)
@@ -46,7 +37,6 @@ void CAgentFolder::LoadFolder(CProxyFolder *folder)
}
}
-
STDMETHODIMP CAgentFolder::LoadItems()
{
if (!_agentSpec->_archiveLink.IsOpen)
@@ -238,6 +228,40 @@ STDMETHODIMP CAgentFolder::BindToParentFolder(IFolderFolder **resultFolder)
COM_TRY_END
}
+STDMETHODIMP CAgentFolder::GetStream(UInt32 index, ISequentialInStream **stream)
+{
+ CMyComPtr<IInArchiveGetStream> getStream;
+ _agentSpec->GetArchive()->QueryInterface(IID_IInArchiveGetStream, (void **)&getStream);
+ if (!getStream)
+ return S_OK;
+
+ const CProxyFolder *folder;
+ UInt32 realIndex;
+ if (_flatMode)
+ {
+ const CProxyItem &item = _items[index];
+ folder = item.Folder;
+ realIndex = item.Index;
+ }
+ else
+ {
+ folder = _proxyFolderItem;
+ realIndex = index;
+ }
+
+ UInt32 indexInArchive;
+ if (realIndex < (UInt32)folder->Folders.Size())
+ {
+ const CProxyFolder &item = folder->Folders[realIndex];
+ if (!item.IsLeaf)
+ return S_OK;
+ indexInArchive = item.Index;
+ }
+ else
+ indexInArchive = folder->Files[realIndex - folder->Folders.Size()].Index;
+ return getStream->GetStream(indexInArchive, stream);
+}
+
STATPROPSTG kProperties[] =
{
{ NULL, kpidNumSubDirs, VT_UI4},
@@ -261,6 +285,8 @@ STDMETHODIMP CAgentFolder::GetNumberOfProperties(UInt32 *numProperties)
*numProperties += kNumProperties;
if (!_flatMode)
(*numProperties)--;
+ if (!_agentSpec->_proxyArchive->ThereIsPathProp)
+ (*numProperties)++;
return S_OK;
COM_TRY_END
}
@@ -270,6 +296,18 @@ STDMETHODIMP CAgentFolder::GetPropertyInfo(UInt32 index, BSTR *name, PROPID *pro
COM_TRY_BEGIN
UInt32 numProperties;
_agentSpec->GetArchive()->GetNumberOfProperties(&numProperties);
+ if (!_agentSpec->_proxyArchive->ThereIsPathProp)
+ {
+ if (index == 0)
+ {
+ *propID = kpidName;
+ *varType = VT_BSTR;
+ *name = 0;
+ return S_OK;
+ }
+ index--;
+ }
+
if (index < numProperties)
{
RINOK(_agentSpec->GetArchive()->GetPropertyInfo(index, name, propID, varType));
@@ -378,7 +416,7 @@ STDMETHODIMP CAgentFolder::Extract(const UInt32 *indices,
NExtract::NPathMode::EEnum pathMode,
NExtract::NOverwriteMode::EEnum overwriteMode,
const wchar_t *path,
- INT32 testMode,
+ Int32 testMode,
IFolderArchiveExtractCallback *extractCallback2)
{
COM_TRY_BEGIN
@@ -399,17 +437,12 @@ STDMETHODIMP CAgentFolder::Extract(const UInt32 *indices,
extractCallbackSpec->InitForMulti(false, pathMode, overwriteMode);
- extractCallbackSpec->Init(_agentSpec->GetArchive(),
+ extractCallbackSpec->Init(NULL, &_agentSpec->GetArc(),
extractCallback2,
- false,
+ false, testMode ? true : false, false,
(path ? path : L""),
pathParts,
- _agentSpec->DefaultName,
- _agentSpec->DefaultTime,
- _agentSpec->DefaultAttrib,
- (UInt64)(Int64)-1
- // ,_agentSpec->_srcDirectoryPrefix
- );
+ (UInt64)(Int64)-1);
CUIntVector realIndices;
GetRealIndices(indices, numItems, realIndices);
return _agentSpec->GetArchive()->Extract(&realIndices.Front(),
@@ -433,18 +466,21 @@ CAgent::~CAgent()
}
STDMETHODIMP CAgent::Open(
+ IInStream *inStream,
const wchar_t *filePath,
BSTR *archiveType,
- // CLSID *clsIDResult,
IArchiveOpenCallback *openArchiveCallback)
{
COM_TRY_BEGIN
_archiveFilePath = filePath;
- NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(_archiveFilePath, fileInfo))
- return ::GetLastError();
- if (fileInfo.IsDir())
- return E_FAIL;
+ NFile::NFind::CFileInfoW fi;
+ if (!inStream)
+ {
+ if (!fi.Find(_archiveFilePath))
+ return ::GetLastError();
+ if (fi.IsDir())
+ return E_FAIL;
+ }
CArcInfoEx archiverInfo0, archiverInfo1;
_compressCodecsInfo.Release();
@@ -452,14 +488,16 @@ STDMETHODIMP CAgent::Open(
_compressCodecsInfo = _codecs;
RINOK(_codecs->Load());
- RINOK(OpenArchive(_codecs, CIntVector(), _archiveFilePath, _archiveLink, openArchiveCallback));
- // _archive = _archiveLink.GetArchive();
- DefaultName = _archiveLink.GetDefaultItemName();
- const CArcInfoEx &ai = _codecs->Formats[_archiveLink.GetArchiverIndex()];
+ RINOK(_archiveLink.Open(_codecs, CIntVector(), false, inStream, _archiveFilePath, openArchiveCallback));
- DefaultTime = fileInfo.MTime;
- DefaultAttrib = fileInfo.Attrib;
- ArchiveType = ai.Name;
+ CArc &arc = _archiveLink.Arcs.Back();
+ if (!inStream)
+ {
+ arc.MTimeDefined = !fi.IsDevice;
+ arc.MTime = fi.MTime;
+ }
+
+ ArchiveType = _codecs->Formats[arc.FormatIndex].Name;
if (archiveType == 0)
return S_OK;
return StringToBstr(ArchiveType, archiveType);
@@ -474,7 +512,7 @@ STDMETHODIMP CAgent::ReOpen(IArchiveOpenCallback *openArchiveCallback)
delete _proxyArchive;
_proxyArchive = NULL;
}
- RINOK(ReOpenArchive(_codecs, _archiveLink, _archiveFilePath, openArchiveCallback));
+ RINOK(_archiveLink.ReOpen(_codecs, _archiveFilePath, openArchiveCallback));
return ReadItems();
COM_TRY_END
}
@@ -482,13 +520,7 @@ STDMETHODIMP CAgent::ReOpen(IArchiveOpenCallback *openArchiveCallback)
STDMETHODIMP CAgent::Close()
{
COM_TRY_BEGIN
- RINOK(_archiveLink.Close());
- if (_archiveLink.GetNumLevels() > 1)
- {
- // return S_OK;
- }
- // _archive->Close();
- return S_OK;
+ return _archiveLink.Close();
COM_TRY_END
}
@@ -504,11 +536,7 @@ HRESULT CAgent::ReadItems()
if (_proxyArchive != NULL)
return S_OK;
_proxyArchive = new CProxyArchive();
- return _proxyArchive->Load(GetArchive(),
- DefaultName,
- // _defaultTime,
- // _defaultAttrib,
- NULL);
+ return _proxyArchive->Load(GetArc(), NULL);
}
STDMETHODIMP CAgent::BindToRootFolder(IFolderFolder **resultFolder)
@@ -528,24 +556,19 @@ STDMETHODIMP CAgent::Extract(
NExtract::NPathMode::EEnum pathMode,
NExtract::NOverwriteMode::EEnum overwriteMode,
const wchar_t *path,
- INT32 testMode,
+ Int32 testMode,
IFolderArchiveExtractCallback *extractCallback2)
{
COM_TRY_BEGIN
CArchiveExtractCallback *extractCallbackSpec = new CArchiveExtractCallback;
CMyComPtr<IArchiveExtractCallback> extractCallback = extractCallbackSpec;
extractCallbackSpec->InitForMulti(false, pathMode, overwriteMode);
- extractCallbackSpec->Init(GetArchive(),
+ extractCallbackSpec->Init(NULL, &GetArc(),
extractCallback2,
- false,
+ false, testMode ? true : false, false,
path,
UStringVector(),
- DefaultName,
- DefaultTime,
- DefaultAttrib,
- (UInt64)(Int64)-1
- // ,_srcDirectoryPrefix
- );
+ (UInt64)(Int64)-1);
return GetArchive()->Extract(0, (UInt32)(Int32)-1, testMode, extractCallback);
COM_TRY_END
}
@@ -590,4 +613,3 @@ STDMETHODIMP CAgent::GetArchivePropertyInfo(UInt32 index,
name, propID, varType);
COM_TRY_END
}
-
diff --git a/CPP/7zip/UI/Agent/Agent.h b/CPP/7zip/UI/Agent/Agent.h
index 64fb31f6..b95725e4 100755
--- a/CPP/7zip/UI/Agent/Agent.h
+++ b/CPP/7zip/UI/Agent/Agent.h
@@ -4,19 +4,20 @@
#define __AGENT_AGENT_H
#include "Common/MyCom.h"
+
#include "Windows/PropVariant.h"
-#include "../Common/UpdateAction.h"
#include "../Common/OpenArchive.h"
-
-#include "IFolderArchive.h"
-#include "AgentProxy.h"
+#include "../Common/UpdateAction.h"
#ifdef NEW_FOLDER_INTERFACE
#include "../FileManager/IFolder.h"
#include "../Common/LoadCodecs.h"
#endif
+#include "AgentProxy.h"
+#include "IFolderArchive.h"
+
class CAgentFolder;
DECL_INTERFACE(IArchiveFolderInternal, 0x01, 0xC)
@@ -38,6 +39,7 @@ class CAgentFolder:
public IGetFolderArchiveProperties,
public IArchiveFolder,
public IArchiveFolderInternal,
+ public IInArchiveGetStream,
#ifdef NEW_FOLDER_INTERFACE
public IFolderOperations,
public IFolderSetFlatMode,
@@ -52,6 +54,7 @@ public:
MY_QUERYINTERFACE_ENTRY(IGetFolderArchiveProperties)
MY_QUERYINTERFACE_ENTRY(IArchiveFolder)
MY_QUERYINTERFACE_ENTRY(IArchiveFolderInternal)
+ MY_QUERYINTERFACE_ENTRY(IInArchiveGetStream)
#ifdef NEW_FOLDER_INTERFACE
MY_QUERYINTERFACE_ENTRY(IFolderOperations)
MY_QUERYINTERFACE_ENTRY(IFolderSetFlatMode)
@@ -73,11 +76,13 @@ public:
NExtract::NPathMode::EEnum pathMode,
NExtract::NOverwriteMode::EEnum overwriteMode,
const wchar_t *path,
- INT32 testMode,
+ Int32 testMode,
IFolderArchiveExtractCallback *extractCallback);
STDMETHOD(GetAgentFolder)(CAgentFolder **agentFolder);
+ STDMETHOD(GetStream)(UInt32 index, ISequentialInStream **stream);
+
#ifdef NEW_FOLDER_INTERFACE
INTERFACE_FolderOperations(;)
@@ -170,7 +175,7 @@ public:
IFolderArchiveUpdateCallback *updateCallback100);
// ISetProperties
- STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, INT32 numProperties);
+ STDMETHOD(SetProperties)(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties);
#endif
CCodecs *_codecs;
@@ -182,14 +187,8 @@ private:
HRESULT ReadItems();
public:
CProxyArchive *_proxyArchive;
-
CArchiveLink _archiveLink;
- // IInArchive *_archive2;
-
- UString DefaultName;
- FILETIME DefaultTime;
- DWORD DefaultAttrib;
UString ArchiveType;
@@ -206,8 +205,9 @@ public:
CObjectVector<NWindows::NCOM::CPropVariant> m_PropValues;
#endif
- IInArchive *GetArchive() { return _archiveLink.GetArchive(); }
- bool CanUpdate() const { return _archiveLink.GetNumLevels() <= 1; }
+ const CArc &GetArc() { return _archiveLink.Arcs.Back(); }
+ IInArchive *GetArchive() { return GetArc().Archive; }
+ bool CanUpdate() const { return _archiveLink.Arcs.Size() == 1; }
};
#ifdef NEW_FOLDER_INTERFACE
diff --git a/CPP/7zip/UI/Agent/AgentOut.cpp b/CPP/7zip/UI/Agent/AgentOut.cpp
index ffeac1c6..51a5affa 100755
--- a/CPP/7zip/UI/Agent/AgentOut.cpp
+++ b/CPP/7zip/UI/Agent/AgentOut.cpp
@@ -27,12 +27,6 @@
using namespace NWindows;
using namespace NCOM;
-static HRESULT CopyBlock(ISequentialInStream *inStream, ISequentialOutStream *outStream)
-{
- CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
- return copyCoder->Code(inStream, outStream, NULL, NULL, NULL);
-}
-
STDMETHODIMP CAgent::SetFolder(IFolderFolder *folder)
{
_archiveNamePrefix.Empty();
@@ -86,20 +80,6 @@ STDMETHODIMP CAgent::SetFiles(const wchar_t *folderPrefix,
return S_OK;
}
-
-static HRESULT GetFileTime(CAgent *agent, UInt32 itemIndex, FILETIME &fileTime)
-{
- CPropVariant property;
- RINOK(agent->GetArchive()->GetProperty(itemIndex, kpidMTime, &property));
- if (property.vt == VT_FILETIME)
- fileTime = property.filetime;
- else if (property.vt == VT_EMPTY)
- fileTime = agent->DefaultTime;
- else
- throw 4190407;
- return S_OK;
-}
-
static HRESULT EnumerateArchiveItems(CAgent *agent,
const CProxyFolder &item,
const UString &prefix,
@@ -110,8 +90,7 @@ static HRESULT EnumerateArchiveItems(CAgent *agent,
{
const CProxyFile &fileItem = item.Files[i];
CArcItem ai;
-
- RINOK(::GetFileTime(agent, fileItem.Index, ai.MTime));
+ RINOK(agent->GetArc().GetItemMTime(fileItem.Index, ai.MTime, ai.MTimeDefined));
CPropVariant property;
agent->GetArchive()->GetProperty(fileItem.Index, kpidSize, &property);
@@ -128,10 +107,10 @@ static HRESULT EnumerateArchiveItems(CAgent *agent,
{
const CProxyFolder &dirItem = item.Folders[i];
UString fullName = prefix + dirItem.Name;
- if(dirItem.IsLeaf)
+ if (dirItem.IsLeaf)
{
CArcItem ai;
- RINOK(::GetFileTime(agent, dirItem.Index, ai.MTime));
+ RINOK(agent->GetArc().GetItemMTime(dirItem.Index, ai.MTime, ai.MTimeDefined));
ai.IsDir = true;
ai.SizeDefined = false;
ai.Name = fullName;
@@ -149,7 +128,7 @@ struct CAgUpCallbackImp: public IUpdateProduceCallback
const CObjectVector<CArcItem> *_arcItems;
IFolderArchiveUpdateCallback *_callback;
- CAgUpCallbackImp(const CObjectVector<CArcItem> *a,
+ CAgUpCallbackImp(const CObjectVector<CArcItem> *a,
IFolderArchiveUpdateCallback *callback): _arcItems(a), _callback(callback) {}
HRESULT ShowDeleteFile(int arcIndex);
};
@@ -268,7 +247,7 @@ STDMETHODIMP CAgent::DoOperation(
{
UString resultPath;
int pos;
- if(!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
+ if (!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
return E_FAIL;
NFile::NDirectory::CreateComplexDirectory(resultPath.Left(pos));
}
@@ -316,7 +295,7 @@ STDMETHODIMP CAgent::DoOperation(
if (!sfxStreamSpec->Open(sfxModule))
return E_FAIL;
// throw "Can't open sfx module";
- RINOK(CopyBlock(sfxStream, outStream));
+ RINOK(NCompress::CopyStream(sfxStream, outStream, NULL));
}
RINOK(outArchive->UpdateItems(outStream, updatePairs2.Size(),updateCallback));
@@ -350,7 +329,7 @@ HRESULT CAgent::CommonUpdate(
{
UString resultPath;
int pos;
- if(!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
+ if (!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
throw 141716;
NFile::NDirectory::CreateComplexDirectory(resultPath.Left(pos));
}
@@ -362,8 +341,8 @@ HRESULT CAgent::CommonUpdate(
resultName = newArchiveName;
if (i > 0)
{
- wchar_t s[32];
- ConvertUInt64ToString(i, s);
+ wchar_t s[16];
+ ConvertUInt32ToString(i, s);
resultName += s;
}
if (outStreamSpec->Open(realPath))
@@ -515,11 +494,11 @@ HRESULT CAgent::RenameItem(
CUpdatePair2 up2;
up2.NewData = false;
up2.NewProps = true;
- RINOK(IsArchiveItemAnti(GetArchive(), i, up2.IsAnti));
+ RINOK(GetArc().IsItemAnti(i, up2.IsAnti));
up2.ArcIndex = i;
UString oldFullPath;
- RINOK(GetArchiveItemPath(GetArchive(), i, DefaultName, oldFullPath));
+ RINOK(GetArc().GetItemPath(i, oldFullPath));
if (oldItemPath.CompareNoCase(oldFullPath.Left(oldItemPath.Length())) != 0)
return E_INVALIDARG;
@@ -543,7 +522,7 @@ HRESULT CAgent::RenameItem(
}
STDMETHODIMP CAgent::SetProperties(const wchar_t **names,
- const PROPVARIANT *values, INT32 numProperties)
+ const PROPVARIANT *values, Int32 numProperties)
{
m_PropNames.Clear();
m_PropValues.Clear();
diff --git a/CPP/7zip/UI/Agent/AgentProxy.cpp b/CPP/7zip/UI/Agent/AgentProxy.cpp
index 0a2de592..9686cf34 100755
--- a/CPP/7zip/UI/Agent/AgentProxy.cpp
+++ b/CPP/7zip/UI/Agent/AgentProxy.cpp
@@ -2,18 +2,14 @@
#include "StdAfx.h"
-#include "AgentProxy.h"
+#include "../../../../C/Sort.h"
-#include "Common/MyCom.h"
#include "Windows/PropVariant.h"
#include "Windows/PropVariantConversions.h"
-#include "Windows/Defs.h"
+
#include "../Common/OpenArchive.h"
-extern "C"
-{
- #include "../../../../C/Sort.h"
-}
+#include "AgentProxy.h"
using namespace NWindows;
@@ -58,7 +54,7 @@ CProxyFolder* CProxyFolder::AddDirSubItem(UInt32 index, bool leaf, const UString
if (folderIndex >= 0)
{
CProxyFolder *item = &Folders[folderIndex];
- if(leaf)
+ if (leaf)
{
item->Index = index;
item->IsLeaf = true;
@@ -116,16 +112,16 @@ void CProxyFolder::AddRealIndices(CUIntVector &realIndices) const
if (IsLeaf)
realIndices.Add(Index);
int i;
- for(i = 0; i < Folders.Size(); i++)
+ for (i = 0; i < Folders.Size(); i++)
Folders[i].AddRealIndices(realIndices);
- for(i = 0; i < Files.Size(); i++)
+ for (i = 0; i < Files.Size(); i++)
realIndices.Add(Files[i].Index);
}
void CProxyFolder::GetRealIndices(const UInt32 *indices, UInt32 numItems, CUIntVector &realIndices) const
{
realIndices.Clear();
- for(UInt32 i = 0; i < numItems; i++)
+ for (UInt32 i = 0; i < numItems; i++)
{
int index = indices[i];
int numDirItems = Folders.Size();
@@ -140,24 +136,6 @@ void CProxyFolder::GetRealIndices(const UInt32 *indices, UInt32 numItems, CUIntV
///////////////////////////////////////////////
// CProxyArchive
-HRESULT CProxyArchive::Reload(IInArchive *archive, IProgress *progress)
-{
- RootFolder.Clear();
- return ReadObjects(archive, progress);
-}
-
-HRESULT CProxyArchive::Load(IInArchive *archive,
- const UString &defaultName,
- // const FILETIME &defaultTime,
- // UInt32 defaultAttributes,
- IProgress *progress)
-{
- DefaultName = defaultName;
- // DefaultTime = defaultTime;
- // DefaultAttributes = defaultAttributes;
- return Reload(archive, progress);
-}
-
static UInt64 GetSize(IInArchive *archive, UInt32 index, PROPID propID)
{
NCOM::CPropVariant prop;
@@ -182,13 +160,8 @@ void CProxyFolder::CalculateSizes(IInArchive *archive)
PackSize += GetSize(archive, index, kpidPackSize);
{
NCOM::CPropVariant prop;
- if (archive->GetProperty(index, kpidCRC, &prop) == S_OK)
- {
- if (prop.vt == VT_UI4)
- Crc += prop.ulVal;
- else
- CrcIsDefined = false;
- }
+ if (archive->GetProperty(index, kpidCRC, &prop) == S_OK && prop.vt == VT_UI4)
+ Crc += prop.ulVal;
else
CrcIsDefined = false;
}
@@ -207,70 +180,67 @@ void CProxyFolder::CalculateSizes(IInArchive *archive)
}
}
-HRESULT CProxyArchive::ReadObjects(IInArchive *archive, IProgress *progress)
+HRESULT CProxyArchive::Load(const CArc &arc, IProgress *progress)
{
+ RootFolder.Clear();
+ IInArchive *archive = arc.Archive;
+ {
+ ThereIsPathProp = false;
+ UInt32 numProps;
+ archive->GetNumberOfProperties(&numProps);
+ for (UInt32 i = 0; i < numProps; i++)
+ {
+ CMyComBSTR name;
+ PROPID propID;
+ VARTYPE varType;
+ RINOK(archive->GetPropertyInfo(i, &name, &propID, &varType));
+ if (propID == kpidPath)
+ {
+ ThereIsPathProp = true;
+ break;
+ }
+ }
+ }
+
UInt32 numItems;
RINOK(archive->GetNumberOfItems(&numItems));
if (progress != NULL)
{
- UINT64 totalItems = numItems;
+ UInt64 totalItems = numItems;
RINOK(progress->SetTotal(totalItems));
}
- for(UInt32 i = 0; i < numItems; i++)
+ UString fileName;
+ for (UInt32 i = 0; i < numItems; i++)
{
- if (progress != NULL)
+ if (progress != NULL && (i & 0xFFFFF) == 0)
{
- UINT64 currentItemIndex = i;
+ UInt64 currentItemIndex = i;
RINOK(progress->SetCompleted(&currentItemIndex));
}
- NCOM::CPropVariant propVariantPath;
- RINOK(archive->GetProperty(i, kpidPath, &propVariantPath));
- CProxyFolder *currentItem = &RootFolder;
- UString fileName;
- if(propVariantPath.vt == VT_EMPTY)
+ UString filePath;
+ RINOK(arc.GetItemPath(i, filePath));
+ CProxyFolder *curItem = &RootFolder;
+ int len = filePath.Length();
+ fileName.Empty();
+ for (int j = 0; j < len; j++)
{
- fileName = DefaultName;
-
- NCOM::CPropVariant prop;
- RINOK(archive->GetProperty(i, kpidExtension, &prop));
- if (prop.vt == VT_BSTR)
+ wchar_t c = filePath[j];
+ if (c == WCHAR_PATH_SEPARATOR || c == L'/')
{
- fileName += L'.';
- fileName += prop.bstrVal;
- }
- else if (prop.vt != VT_EMPTY)
- return E_FAIL;
-
- }
- else
- {
- if(propVariantPath.vt != VT_BSTR)
- return E_FAIL;
- UString filePath = propVariantPath.bstrVal;
-
- int len = filePath.Length();
- for (int i = 0; i < len; i++)
- {
- wchar_t c = filePath[i];
- if (c == WCHAR_PATH_SEPARATOR || c == L'/')
- {
- currentItem = currentItem->AddDirSubItem((UInt32)(Int32)-1, false, fileName);
- fileName.Empty();
- }
- else
- fileName += c;
+ curItem = curItem->AddDirSubItem((UInt32)(Int32)-1, false, fileName);
+ fileName.Empty();
}
+ else
+ fileName += c;
}
- NCOM::CPropVariant propVariantIsFolder;
bool isFolder;
RINOK(IsArchiveItemFolder(archive, i, isFolder));
- if(isFolder)
- currentItem->AddDirSubItem(i, true, fileName);
+ if (isFolder)
+ curItem->AddDirSubItem(i, true, fileName);
else
- currentItem->AddFileSubItem(i, fileName);
+ curItem->AddFileSubItem(i, fileName);
}
RootFolder.CalculateSizes(archive);
return S_OK;
}
-
diff --git a/CPP/7zip/UI/Agent/AgentProxy.h b/CPP/7zip/UI/Agent/AgentProxy.h
index a0111088..d4caca16 100755
--- a/CPP/7zip/UI/Agent/AgentProxy.h
+++ b/CPP/7zip/UI/Agent/AgentProxy.h
@@ -5,18 +5,16 @@
#include "Common/MyString.h"
-#include "../../Archive/IArchive.h"
+#include "../Common/OpenArchive.h"
-class CProxyFile
+struct CProxyFile
{
-public:
UInt32 Index;
UString Name;
};
-class CProxyFolder: public CProxyFile
+struct CProxyFolder: public CProxyFile
{
-public:
CProxyFolder *Parent;
CObjectVector<CProxyFolder> Folders;
CObjectVector<CProxyFile> Files;
@@ -44,20 +42,12 @@ public:
void CalculateSizes(IInArchive *archive);
};
-class CProxyArchive
+struct CProxyArchive
{
- HRESULT ReadObjects(IInArchive *archive, IProgress *progress);
-public:
- UString DefaultName;
- // FILETIME DefaultTime;
- // UInt32 DefaultAttributes;
CProxyFolder RootFolder;
- HRESULT Reload(IInArchive *archive, IProgress *progress);
- HRESULT Load(IInArchive *archive,
- const UString &defaultName,
- // const FILETIME &defaultTime,
- // UInt32 defaultAttributes,
- IProgress *progress);
+ bool ThereIsPathProp;
+
+ HRESULT Load(const CArc &arc, IProgress *progress);
};
-#endif \ No newline at end of file
+#endif
diff --git a/CPP/7zip/UI/Agent/ArchiveFolder.cpp b/CPP/7zip/UI/Agent/ArchiveFolder.cpp
index 780d26b8..57975e7d 100755
--- a/CPP/7zip/UI/Agent/ArchiveFolder.cpp
+++ b/CPP/7zip/UI/Agent/ArchiveFolder.cpp
@@ -1,17 +1,9 @@
-// Zip/ArchiveFolder.cpp
+// Agent/ArchiveFolder.cpp
#include "StdAfx.h"
#include "Common/ComTry.h"
-#include "Common/StringConvert.h"
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
-#include "Windows/PropVariantConversions.h"
-#include "Windows/FileDir.h"
-#include "../../Common/FileStreams.h"
-
-#include "../Common/UpdatePair.h"
#include "../Common/ArchiveExtractCallback.h"
#include "Agent.h"
@@ -19,7 +11,7 @@
using namespace NWindows;
using namespace NCOM;
-STDMETHODIMP CAgentFolder::CopyTo(const UINT32 *indices, UINT32 numItems,
+STDMETHODIMP CAgentFolder::CopyTo(const UInt32 *indices, UInt32 numItems,
const wchar_t *path, IFolderOperationsExtractCallback *callback)
{
COM_TRY_BEGIN
@@ -46,18 +38,12 @@ STDMETHODIMP CAgentFolder::CopyTo(const UINT32 *indices, UINT32 numItems,
NExtract::NPathMode::kCurrentPathnames;
extractCallbackSpec->InitForMulti(false, pathMode, NExtract::NOverwriteMode::kAskBefore);
- extractCallbackSpec->Init(_agentSpec->GetArchive(),
+ extractCallbackSpec->Init(NULL, &_agentSpec->GetArc(),
extractCallback2,
- false,
+ false, false, false,
path,
pathParts,
- _agentSpec->DefaultName,
- _agentSpec->DefaultTime,
- _agentSpec->DefaultAttrib,
- (UInt64)(Int64)-1
-
- // ,_agentSpec->_srcDirectoryPrefix
- );
+ (UInt64)(Int64)-1);
CUIntVector realIndices;
GetRealIndices(indices, numItems, realIndices);
return _agentSpec->GetArchive()->Extract(&realIndices.Front(),
@@ -65,7 +51,7 @@ STDMETHODIMP CAgentFolder::CopyTo(const UINT32 *indices, UINT32 numItems,
COM_TRY_END
}
-STDMETHODIMP CAgentFolder::MoveTo(const UINT32 * /* indices */, UINT32 /* numItems */,
+STDMETHODIMP CAgentFolder::MoveTo(const UInt32 * /* indices */, UInt32 /* numItems */,
const wchar_t * /* path */, IFolderOperationsExtractCallback * /* callback */)
{
return E_NOTIMPL;
diff --git a/CPP/7zip/UI/Agent/ArchiveFolderOpen.cpp b/CPP/7zip/UI/Agent/ArchiveFolderOpen.cpp
index f339a287..98c75f4d 100755
--- a/CPP/7zip/UI/Agent/ArchiveFolderOpen.cpp
+++ b/CPP/7zip/UI/Agent/ArchiveFolderOpen.cpp
@@ -6,8 +6,6 @@
#include "Common/StringConvert.h"
-#include "../Common/OpenArchive.h"
-
static inline UINT GetCurrentFileCodePage()
{ return AreFileApisANSI() ? CP_ACP : CP_OEMCP; }
@@ -28,7 +26,7 @@ int CArchiveFolderManager::FindFormat(const UString &type)
return -1;
}
-STDMETHODIMP CArchiveFolderManager::OpenFolderFile(const wchar_t *filePath,
+STDMETHODIMP CArchiveFolderManager::OpenFolderFile(IInStream *inStream, const wchar_t *filePath,
IFolderFolder **resultFolder, IProgress *progress)
{
CMyComPtr<IArchiveOpenCallback> openArchiveCallback;
@@ -39,7 +37,7 @@ STDMETHODIMP CArchiveFolderManager::OpenFolderFile(const wchar_t *filePath,
}
CAgent *agent = new CAgent();
CMyComPtr<IInFolderArchive> archive = agent;
- RINOK(agent->Open(filePath, NULL, openArchiveCallback));
+ RINOK(agent->Open(inStream, filePath, NULL, openArchiveCallback));
return agent->BindToRootFolder(resultFolder);
}
diff --git a/CPP/7zip/UI/Agent/ArchiveFolderOut.cpp b/CPP/7zip/UI/Agent/ArchiveFolderOut.cpp
index 304dce83..8f03f44d 100755
--- a/CPP/7zip/UI/Agent/ArchiveFolderOut.cpp
+++ b/CPP/7zip/UI/Agent/ArchiveFolderOut.cpp
@@ -1,17 +1,15 @@
// FolderOut.cpp
#include "StdAfx.h"
-#include "Agent.h"
-#include "Common/StringConvert.h"
#include "Common/ComTry.h"
+
#include "Windows/FileDir.h"
-// #include "../Common/CompressEngineCommon.h"
-#include "../Common/ZipRegistry.h"
-#include "../Common/UpdateAction.h"
#include "../Common/WorkDir.h"
+#include "Agent.h"
+
using namespace NWindows;
using namespace NFile;
using namespace NDirectory;
@@ -35,7 +33,7 @@ HRESULT CAgentFolder::CommonUpdateOperation(
NWorkDir::CInfo workDirInfo;
ReadWorkDirInfo(workDirInfo);
UString archiveFilePath = _agentSpec->_archiveFilePath;
- UString workDir = GetWorkDir(workDirInfo, archiveFilePath );
+ UString workDir = GetWorkDir(workDirInfo, archiveFilePath);
CreateComplexDirectory(workDir);
CTempFileW tempFile;
@@ -86,11 +84,12 @@ HRESULT CAgentFolder::CommonUpdateOperation(
// m_FolderItem = NULL;
- if (!DeleteFileAlways(archiveFilePath ))
- return GetLastError();
+ if (NFind::DoesFileExist(archiveFilePath))
+ if (!DeleteFileAlways(archiveFilePath))
+ return GetLastError();
tempFile.DisableDeleting();
- if (!MyMoveFile(tempFileName, archiveFilePath ))
+ if (!MyMoveFile(tempFileName, archiveFilePath))
return GetLastError();
{
@@ -134,17 +133,23 @@ STDMETHODIMP CAgentFolder::CopyFrom(
IProgress *progress)
{
COM_TRY_BEGIN
- RINOK(_agentSpec->SetFiles(fromFolderPath, itemsPaths, numItems));
- RINOK(_agentSpec->SetFolder(this));
CMyComPtr<IFolderArchiveUpdateCallback> updateCallback100;
if (progress != 0)
{
- CMyComPtr<IProgress> progressWrapper = progress;
- RINOK(progressWrapper.QueryInterface(
- IID_IFolderArchiveUpdateCallback, &updateCallback100));
+ RINOK(progress->QueryInterface(IID_IFolderArchiveUpdateCallback, (void **)&updateCallback100));
+ }
+ try
+ {
+ RINOK(_agentSpec->SetFiles(fromFolderPath, itemsPaths, numItems));
+ RINOK(_agentSpec->SetFolder(this));
+ return CommonUpdateOperation(false, false, false, NULL,
+ &NUpdateArchive::kAddActionSet, 0, 0, updateCallback100);
+ }
+ catch(const UString &s)
+ {
+ RINOK(updateCallback100->UpdateErrorMessage(UString(L"Error: ") + s));
+ return E_FAIL;
}
- return CommonUpdateOperation(false, false, false, NULL,
- &NUpdateArchive::kAddActionSet, 0, 0, updateCallback100);
COM_TRY_END
}
diff --git a/CPP/7zip/UI/Agent/IFolderArchive.h b/CPP/7zip/UI/Agent/IFolderArchive.h
index 7bb12482..91da1150 100755
--- a/CPP/7zip/UI/Agent/IFolderArchive.h
+++ b/CPP/7zip/UI/Agent/IFolderArchive.h
@@ -3,14 +3,13 @@
#ifndef __IFOLDER_ARCHIVE_H
#define __IFOLDER_ARCHIVE_H
+#include "../../IDecl.h"
#include "../../Archive/IArchive.h"
-// #include "../Format/Common/ArchiveInterface.h"
-#include "../../UI/FileManager/IFolder.h"
-#include "../Common/IFileExtractCallback.h"
-#include "../Common/ExtractMode.h"
#include "../../UI/Common/LoadCodecs.h"
+#include "../../UI/FileManager/IFolder.h"
-#include "../../IDecl.h"
+#include "../Common/ExtractMode.h"
+#include "../Common/IFileExtractCallback.h"
#define FOLDER_ARCHIVE_INTERFACE_SUB(i, base, x) DECL_INTERFACE_SUB(i, base, 0x01, x)
#define FOLDER_ARCHIVE_INTERFACE(i, x) FOLDER_ARCHIVE_INTERFACE_SUB(i, IUnknown, x)
@@ -28,7 +27,7 @@ FOLDER_ARCHIVE_INTERFACE(IArchiveFolder, 0x05)
};
#define INTERFACE_IInFolderArchive(x) \
- STDMETHOD(Open)(const wchar_t *filePath, BSTR *archiveType, IArchiveOpenCallback *openArchiveCallback) x; \
+ STDMETHOD(Open)(IInStream *inStream, const wchar_t *filePath, BSTR *archiveType, IArchiveOpenCallback *openArchiveCallback) x; \
STDMETHOD(ReOpen)(IArchiveOpenCallback *openArchiveCallback) x; \
STDMETHOD(Close)() x; \
STDMETHOD(GetNumberOfProperties)(UInt32 *numProperties) x; \
@@ -38,7 +37,7 @@ FOLDER_ARCHIVE_INTERFACE(IArchiveFolder, 0x05)
NExtract::NOverwriteMode::EEnum overwriteMode, const wchar_t *path, \
Int32 testMode, IFolderArchiveExtractCallback *extractCallback2) x; \
-FOLDER_ARCHIVE_INTERFACE(IInFolderArchive, 0x06)
+FOLDER_ARCHIVE_INTERFACE(IInFolderArchive, 0x0D)
{
INTERFACE_IInFolderArchive(PURE)
};
diff --git a/CPP/7zip/UI/Agent/UpdateCallbackAgent.cpp b/CPP/7zip/UI/Agent/UpdateCallbackAgent.cpp
index e14197d2..21549c90 100755
--- a/CPP/7zip/UI/Agent/UpdateCallbackAgent.cpp
+++ b/CPP/7zip/UI/Agent/UpdateCallbackAgent.cpp
@@ -90,19 +90,29 @@ HRESULT CUpdateCallbackAgent::SetOperationResult(Int32 operationResult)
HRESULT CUpdateCallbackAgent::CryptoGetTextPassword2(Int32 *passwordIsDefined, BSTR *password)
{
+ *password = NULL;
*passwordIsDefined = BoolToInt(false);
if (!_cryptoGetTextPassword)
{
if (!Callback)
return S_OK;
- HRESULT result = Callback.QueryInterface(
- IID_ICryptoGetTextPassword2, &_cryptoGetTextPassword);
- if (result != S_OK)
+ Callback.QueryInterface(IID_ICryptoGetTextPassword2, &_cryptoGetTextPassword);
+ if (!_cryptoGetTextPassword)
return S_OK;
}
return _cryptoGetTextPassword->CryptoGetTextPassword2(passwordIsDefined, password);
}
+HRESULT CUpdateCallbackAgent::CryptoGetTextPassword(BSTR *password)
+{
+ *password = NULL;
+ CMyComPtr<ICryptoGetTextPassword> getTextPassword;
+ Callback.QueryInterface(IID_ICryptoGetTextPassword, &getTextPassword);
+ if (!getTextPassword)
+ return E_NOTIMPL;
+ return getTextPassword->CryptoGetTextPassword(password);
+}
+
/*
HRESULT CUpdateCallbackAgent::ShowDeleteFile(const wchar_t *name)
{
diff --git a/CPP/7zip/UI/Client7z/Client7z.cpp b/CPP/7zip/UI/Client7z/Client7z.cpp
index a63144a7..7c052171 100755
--- a/CPP/7zip/UI/Client7z/Client7z.cpp
+++ b/CPP/7zip/UI/Client7z/Client7z.cpp
@@ -330,7 +330,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index,
else
{
NFile::NFind::CFileInfoW fi;
- if (NFile::NFind::FindFile(fullProcessedPath, fi))
+ if (fi.Find(fullProcessedPath))
{
if (!NFile::NDirectory::DeleteFileAlways(fullProcessedPath))
{
@@ -621,8 +621,8 @@ STDMETHODIMP CArchiveUpdateCallback::GetVolumeSize(UInt32 index, UInt64 *size)
STDMETHODIMP CArchiveUpdateCallback::GetVolumeStream(UInt32 index, ISequentialOutStream **volumeStream)
{
- wchar_t temp[32];
- ConvertUInt64ToString(index + 1, temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(index + 1, temp);
UString res = temp;
while (res.Length() < 2)
res = UString(L'0') + res;
@@ -707,7 +707,7 @@ int MY_CDECL main(int argc, char* argv[])
UString name = GetUnicodeString(argv[i], CP_OEMCP);
NFile::NFind::CFileInfoW fi;
- if (!NFile::NFind::FindFile(name, fi))
+ if (!fi.Find(name))
{
PrintString(UString(L"Can't find file") + name);
return 1;
diff --git a/CPP/7zip/UI/Common/ArchiveCommandLine.cpp b/CPP/7zip/UI/Common/ArchiveCommandLine.cpp
index 46e8a2a1..96d47c08 100755
--- a/CPP/7zip/UI/Common/ArchiveCommandLine.cpp
+++ b/CPP/7zip/UI/Common/ArchiveCommandLine.cpp
@@ -11,18 +11,18 @@
#include "Common/StringConvert.h"
#include "Common/StringToInt.h"
-#include "Windows/FileName.h"
#include "Windows/FileDir.h"
+#include "Windows/FileName.h"
#ifdef _WIN32
#include "Windows/FileMapping.h"
#include "Windows/Synchronization.h"
#endif
#include "ArchiveCommandLine.h"
-#include "UpdateAction.h"
-#include "Update.h"
-#include "SortUtils.h"
#include "EnumDirItems.h"
+#include "SortUtils.h"
+#include "Update.h"
+#include "UpdateAction.h"
extern bool g_CaseSensitive;
@@ -38,6 +38,8 @@ using namespace NCommandLineParser;
using namespace NWindows;
using namespace NFile;
+int g_CodePage = -1;
+
namespace NKey {
enum Enum
{
@@ -69,10 +71,12 @@ enum Enum
kEmail,
kShowDialog,
kLargePages,
- kCharSet,
+ kListfileCharSet,
+ kConsoleCharSet,
kTechMode,
kShareForWrite,
- kCaseSensitive
+ kCaseSensitive,
+ kCalcCrc,
};
}
@@ -137,9 +141,11 @@ static const CSwitchForm kSwitchForms[] =
{ L"AD", NSwitchType::kSimple, false },
{ L"SLP", NSwitchType::kUnLimitedPostString, false, 0},
{ L"SCS", NSwitchType::kUnLimitedPostString, false, 0},
+ { L"SCC", NSwitchType::kUnLimitedPostString, false, 0},
{ L"SLT", NSwitchType::kSimple, false },
{ L"SSW", NSwitchType::kSimple, false },
- { L"SSC", NSwitchType::kPostChar, false, 0, 0, L"-" }
+ { L"SSC", NSwitchType::kPostChar, false, 0, 0, L"-" },
+ { L"SCRC", NSwitchType::kSimple, false }
};
static const CCommandForm g_CommandForms[] =
@@ -412,9 +418,9 @@ static void ConvertToLongName(const UString &prefix, UString &name)
{
if (name.IsEmpty() || DoesNameContainWildCard(name))
return;
- NFind::CFileInfoW fileInfo;
- if (NFind::FindFile(prefix + name, fileInfo))
- name = fileInfo.Name;
+ NFind::CFileInfoW fi;
+ if (fi.Find(prefix + name))
+ name = fi.Name;
}
static void ConvertToLongNames(const UString &prefix, CObjectVector<NWildcard::CItem> &items)
@@ -698,6 +704,7 @@ void CArchiveCommandLineParser::Parse1(const UStringVector &commandStrings,
options.IsInTerminal = MY_IS_TERMINAL(stdin);
options.IsStdOutTerminal = MY_IS_TERMINAL(stdout);
options.IsStdErrTerminal = MY_IS_TERMINAL(stderr);
+ options.StdInMode = parser[NKey::kStdIn].ThereIs;
options.StdOutMode = parser[NKey::kStdOut].ThereIs;
options.EnableHeaders = !parser[NKey::kDisableHeaders].ThereIs;
options.HelpMode = parser[NKey::kHelp1].ThereIs || parser[NKey::kHelp2].ThereIs || parser[NKey::kHelp3].ThereIs;
@@ -722,11 +729,28 @@ struct CCodePagePair
static CCodePagePair g_CodePagePairs[] =
{
{ L"UTF-8", CP_UTF8 },
- { L"WIN", CP_ACP },
- { L"DOS", CP_OEMCP }
+ { L"WIN", CP_ACP },
+ { L"DOS", CP_OEMCP }
};
-static const int kNumCodePages = sizeof(g_CodePagePairs) / sizeof(g_CodePagePairs[0]);
+static int FindCharset(const NCommandLineParser::CParser &parser, int keyIndex, int defaultVal)
+{
+ if (!parser[keyIndex].ThereIs)
+ return defaultVal;
+
+ UString name = parser[keyIndex].PostStrings.Back();
+ name.MakeUpper();
+ int i;
+ for (i = 0; i < sizeof(g_CodePagePairs) / sizeof(g_CodePagePairs[0]); i++)
+ {
+ const CCodePagePair &pair = g_CodePagePairs[i];
+ if (name.Compare(pair.Name) == 0)
+ return pair.CodePage;
+ }
+ if (i == sizeof(g_CodePagePairs) / sizeof(g_CodePagePairs[0]))
+ ThrowUserErrorException();
+ return -1;
+}
static bool ConvertStringToUInt32(const wchar_t *s, UInt32 &v)
{
@@ -751,6 +775,7 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
ThrowUserErrorException();
options.TechMode = parser[NKey::kTechMode].ThereIs;
+ options.CalcCrc = parser[NKey::kCalcCrc].ThereIs;
if (parser[NKey::kCaseSensitive].ThereIs)
g_CaseSensitive = (parser[NKey::kCaseSensitive].PostCharIndex < 0);
@@ -761,24 +786,8 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
else
recursedType = NRecursedType::kNonRecursed;
- UINT codePage = CP_UTF8;
- if (parser[NKey::kCharSet].ThereIs)
- {
- UString name = parser[NKey::kCharSet].PostStrings.Front();
- name.MakeUpper();
- int i;
- for (i = 0; i < kNumCodePages; i++)
- {
- const CCodePagePair &pair = g_CodePagePairs[i];
- if (name.Compare(pair.Name) == 0)
- {
- codePage = pair.CodePage;
- break;
- }
- }
- if (i >= kNumCodePages)
- ThrowUserErrorException();
- }
+ g_CodePage = FindCharset(parser, NKey::kConsoleCharSet, -1);
+ UINT codePage = FindCharset(parser, NKey::kListfileCharSet, CP_UTF8);
bool thereAreSwitchIncludes = false;
if (parser[NKey::kInclude].ThereIs)
@@ -795,6 +804,13 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
bool thereIsArchiveName = !parser[NKey::kNoArName].ThereIs &&
options.Command.CommandType != NCommandType::kBenchmark &&
options.Command.CommandType != NCommandType::kInfo;
+
+ bool isExtractGroupCommand = options.Command.IsFromExtractGroup();
+ bool isExtractOrList = isExtractGroupCommand || options.Command.CommandType == NCommandType::kList;
+
+ if (isExtractOrList && options.StdInMode)
+ thereIsArchiveName = false;
+
if (thereIsArchiveName)
{
if (curCommandIndex >= numNonSwitchStrings)
@@ -808,7 +824,6 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
options.YesToAll = parser[NKey::kYes].ThereIs;
- bool isExtractGroupCommand = options.Command.IsFromExtractGroup();
#ifndef _NO_CRYPTO
options.PasswordEnabled = parser[NKey::kPassword].ThereIs;
@@ -816,16 +831,13 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
options.Password = parser[NKey::kPassword].PostStrings[0];
#endif
- options.StdInMode = parser[NKey::kStdIn].ThereIs;
options.ShowDialog = parser[NKey::kShowDialog].ThereIs;
if (parser[NKey::kArchiveType].ThereIs)
options.ArcType = parser[NKey::kArchiveType].PostStrings[0];
- if (isExtractGroupCommand || options.Command.CommandType == NCommandType::kList)
+ if (isExtractOrList)
{
- if (options.StdInMode)
- ThrowException("Reading archives from stdin is not implemented");
if (!options.WildcardCensor.AllAreRelative())
ThrowException("Cannot use absolute pathnames for this command");
@@ -849,6 +861,15 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
archiveWildcardCensor.ExtendExclude();
+ if (options.StdInMode)
+ {
+ UString arcName = parser[NKey::kStdIn].PostStrings.Front();
+ options.ArchivePathsSorted.Add(arcName);
+ options.ArchivePathsFullSorted.Add(arcName);
+ }
+ else
+ {
+
UStringVector archivePaths;
{
@@ -889,6 +910,8 @@ void CArchiveCommandLineParser::Parse2(CArchiveCommandLineOptions &options)
options.ArchivePathsSorted.Add(archivePaths[indices[i]]);
options.ArchivePathsFullSorted.Add(archivePathsFull[indices[i]]);
}
+
+ }
if (isExtractGroupCommand)
{
diff --git a/CPP/7zip/UI/Common/ArchiveCommandLine.h b/CPP/7zip/UI/Common/ArchiveCommandLine.h
index 9c37f336..6f79b7ee 100755
--- a/CPP/7zip/UI/Common/ArchiveCommandLine.h
+++ b/CPP/7zip/UI/Common/ArchiveCommandLine.h
@@ -73,6 +73,7 @@ struct CArchiveCommandLineOptions
bool TechMode;
// Extract
+ bool CalcCrc;
bool AppendName;
UString OutputDir;
NExtract::NOverwriteMode::EEnum OverwriteMode;
diff --git a/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp b/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp
index 5af5286b..4c0cc90b 100755
--- a/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp
+++ b/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp
@@ -2,24 +2,19 @@
#include "StdAfx.h"
-#include "ArchiveExtractCallback.h"
-
-#include "Common/Wildcard.h"
-#include "Common/StringConvert.h"
#include "Common/ComTry.h"
+#include "Common/Wildcard.h"
#include "Windows/FileDir.h"
#include "Windows/FileFind.h"
-#include "Windows/Time.h"
-#include "Windows/Defs.h"
#include "Windows/PropVariant.h"
-
#include "Windows/PropVariantConversions.h"
#include "../../Common/FilePathAutoRename.h"
#include "../Common/ExtractingFilePath.h"
-#include "OpenArchive.h"
+
+#include "ArchiveExtractCallback.h"
using namespace NWindows;
@@ -27,20 +22,20 @@ static const wchar_t *kCantAutoRename = L"ERROR: Can not create file with auto n
static const wchar_t *kCantRenameFile = L"ERROR: Can not rename existing file ";
static const wchar_t *kCantDeleteOutputFile = L"ERROR: Can not delete output file ";
-
void CArchiveExtractCallback::Init(
- IInArchive *archiveHandler,
+ const NWildcard::CCensorNode *wildcardCensor,
+ const CArc *arc,
IFolderArchiveExtractCallback *extractCallback2,
- bool stdOutMode,
+ bool stdOutMode, bool testMode, bool crcMode,
const UString &directoryPath,
const UStringVector &removePathParts,
- const UString &itemDefaultName,
- const FILETIME &utcMTimeDefault,
- UInt32 attributesDefault,
UInt64 packSize)
{
+ _wildcardCensor = wildcardCensor;
+
_stdOutMode = stdOutMode;
- _numErrors = 0;
+ _testMode = testMode;
+ _crcMode = crcMode;
_unpTotal = 1;
_packTotal = packSize;
@@ -51,11 +46,9 @@ void CArchiveExtractCallback::Init(
LocalProgressSpec->Init(extractCallback2, true);
LocalProgressSpec->SendProgress = false;
- _itemDefaultName = itemDefaultName;
- _utcMTimeDefault = utcMTimeDefault;
- _attributesDefault = attributesDefault;
+
_removePathParts = removePathParts;
- _archiveHandler = archiveHandler;
+ _arc = arc;
_directoryPath = directoryPath;
NFile::NName::NormalizeDirPathPrefix(_directoryPath);
}
@@ -117,7 +110,7 @@ STDMETHODIMP CArchiveExtractCallback::SetRatioInfo(const UInt64 *inSize, const U
void CArchiveExtractCallback::CreateComplexDirectory(const UStringVector &dirPathParts, UString &fullPath)
{
fullPath = _directoryPath;
- for(int i = 0; i < dirPathParts.Size(); i++)
+ for (int i = 0; i < dirPathParts.Size(); i++)
{
if (i > 0)
fullPath += wchar_t(NFile::NName::kDirDelimiter);
@@ -126,24 +119,11 @@ void CArchiveExtractCallback::CreateComplexDirectory(const UStringVector &dirPat
}
}
-static UString MakePathNameFromParts(const UStringVector &parts)
-{
- UString result;
- for(int i = 0; i < parts.Size(); i++)
- {
- if(i != 0)
- result += wchar_t(NFile::NName::kDirDelimiter);
- result += parts[i];
- }
- return result;
-}
-
-
HRESULT CArchiveExtractCallback::GetTime(int index, PROPID propID, FILETIME &filetime, bool &filetimeIsDefined)
{
filetimeIsDefined = false;
NCOM::CPropVariant prop;
- RINOK(_archiveHandler->GetProperty(index, propID, &prop));
+ RINOK(_arc->Archive->GetProperty(index, propID, &prop));
if (prop.vt == VT_FILETIME)
{
filetime = prop.filetime;
@@ -154,26 +134,40 @@ HRESULT CArchiveExtractCallback::GetTime(int index, PROPID propID, FILETIME &fil
return S_OK;
}
+HRESULT CArchiveExtractCallback::GetUnpackSize()
+{
+ NCOM::CPropVariant prop;
+ RINOK(_arc->Archive->GetProperty(_index, kpidSize, &prop));
+ _curSizeDefined = (prop.vt != VT_EMPTY);
+ if (_curSizeDefined)
+ _curSize = ConvertPropVariantToUInt64(prop);
+ return S_OK;
+}
+
STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStream **outStream, Int32 askExtractMode)
{
COM_TRY_BEGIN
+ _crcStream.Release();
*outStream = 0;
_outFileStream.Release();
_encrypted = false;
_isSplit = false;
_curSize = 0;
+ _curSizeDefined = false;
+ _index = index;
UString fullPath;
- RINOK(GetArchiveItemPath(_archiveHandler, index, _itemDefaultName, fullPath));
- RINOK(IsArchiveItemFolder(_archiveHandler, index, _processedFileInfo.IsDir));
+ IInArchive *archive = _arc->Archive;
+ RINOK(_arc->GetItemPath(index, fullPath));
+ RINOK(IsArchiveItemFolder(archive, index, _fi.IsDir));
_filePath = fullPath;
{
NCOM::CPropVariant prop;
- RINOK(_archiveHandler->GetProperty(index, kpidPosition, &prop));
+ RINOK(archive->GetProperty(index, kpidPosition, &prop));
if (prop.vt != VT_EMPTY)
{
if (prop.vt != VT_UI8)
@@ -183,22 +177,17 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
}
}
- RINOK(IsArchiveItemProp(_archiveHandler, index, kpidEncrypted, _encrypted));
+ RINOK(GetArchiveItemBoolProp(archive, index, kpidEncrypted, _encrypted));
+
+ RINOK(GetUnpackSize());
- bool newFileSizeDefined;
- UInt64 newFileSize;
+ if (_wildcardCensor)
{
- NCOM::CPropVariant prop;
- RINOK(_archiveHandler->GetProperty(index, kpidSize, &prop));
- newFileSizeDefined = (prop.vt != VT_EMPTY);
- if (newFileSizeDefined)
- {
- newFileSize = ConvertPropVariantToUInt64(prop);
- _curSize = newFileSize;
- }
+ if (!_wildcardCensor->CheckPath(fullPath, !_fi.IsDir))
+ return S_OK;
}
- if(askExtractMode == NArchive::NExtract::NAskMode::kExtract)
+ if (askExtractMode == NArchive::NExtract::NAskMode::kExtract && !_testMode)
{
if (_stdOutMode)
{
@@ -209,32 +198,29 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
{
NCOM::CPropVariant prop;
- RINOK(_archiveHandler->GetProperty(index, kpidAttrib, &prop));
- if (prop.vt == VT_EMPTY)
+ RINOK(archive->GetProperty(index, kpidAttrib, &prop));
+ if (prop.vt == VT_UI4)
{
- _processedFileInfo.Attributes = _attributesDefault;
- _processedFileInfo.AttributesAreDefined = false;
+ _fi.Attrib = prop.ulVal;
+ _fi.AttribDefined = true;
}
+ else if (prop.vt == VT_EMPTY)
+ _fi.AttribDefined = false;
else
- {
- if (prop.vt != VT_UI4)
- return E_FAIL;
- _processedFileInfo.Attributes = prop.ulVal;
- _processedFileInfo.AttributesAreDefined = true;
- }
+ return E_FAIL;
}
- RINOK(GetTime(index, kpidCTime, _processedFileInfo.CTime, _processedFileInfo.CTimeDefined));
- RINOK(GetTime(index, kpidATime, _processedFileInfo.ATime, _processedFileInfo.ATimeDefined));
- RINOK(GetTime(index, kpidMTime, _processedFileInfo.MTime, _processedFileInfo.MTimeDefined));
+ RINOK(GetTime(index, kpidCTime, _fi.CTime, _fi.CTimeDefined));
+ RINOK(GetTime(index, kpidATime, _fi.ATime, _fi.ATimeDefined));
+ RINOK(GetTime(index, kpidMTime, _fi.MTime, _fi.MTimeDefined));
bool isAnti = false;
- RINOK(IsArchiveItemProp(_archiveHandler, index, kpidIsAnti, isAnti));
+ RINOK(_arc->IsItemAnti(index, isAnti));
UStringVector pathParts;
SplitPathToParts(fullPath, pathParts);
- if(pathParts.IsEmpty())
+ if (pathParts.IsEmpty())
return E_FAIL;
int numRemovePathParts = 0;
switch(_pathMode)
@@ -262,7 +248,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
UString processedPath = MakePathNameFromParts(pathParts);
if (!isAnti)
{
- if (!_processedFileInfo.IsDir)
+ if (!_fi.IsDir)
{
if (!pathParts.IsEmpty())
pathParts.DeleteBack();
@@ -272,18 +258,18 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
{
UString fullPathNew;
CreateComplexDirectory(pathParts, fullPathNew);
- if (_processedFileInfo.IsDir)
+ if (_fi.IsDir)
NFile::NDirectory::SetDirTime(fullPathNew,
- (WriteCTime && _processedFileInfo.CTimeDefined) ? &_processedFileInfo.CTime : NULL,
- (WriteATime && _processedFileInfo.ATimeDefined) ? &_processedFileInfo.ATime : NULL,
- (WriteMTime && _processedFileInfo.MTimeDefined) ? &_processedFileInfo.MTime : &_utcMTimeDefault);
+ (WriteCTime && _fi.CTimeDefined) ? &_fi.CTime : NULL,
+ (WriteATime && _fi.ATimeDefined) ? &_fi.ATime : NULL,
+ (WriteMTime && _fi.MTimeDefined) ? &_fi.MTime : (_arc->MTimeDefined ? &_arc->MTime : NULL));
}
}
UString fullProcessedPath = _directoryPath + processedPath;
- if(_processedFileInfo.IsDir)
+ if (_fi.IsDir)
{
_diskFilePath = fullProcessedPath;
if (isAnti)
@@ -294,7 +280,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
if (!_isSplit)
{
NFile::NFind::CFileInfoW fileInfo;
- if(NFile::NFind::FindFile(fullProcessedPath, fileInfo))
+ if (fileInfo.Find(fullProcessedPath))
{
switch(_overwriteMode)
{
@@ -305,8 +291,8 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
Int32 overwiteResult;
RINOK(_extractCallback2->AskOverwrite(
fullProcessedPath, &fileInfo.MTime, &fileInfo.Size, fullPath,
- _processedFileInfo.MTimeDefined ? &_processedFileInfo.MTime : NULL,
- newFileSizeDefined ? &newFileSize : NULL,
+ _fi.MTimeDefined ? &_fi.MTime : NULL,
+ _curSizeDefined ? &_curSize : NULL,
&overwiteResult))
switch(overwiteResult)
@@ -349,7 +335,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
RINOK(_extractCallback2->MessageError(message));
return E_FAIL;
}
- if(!NFile::NDirectory::MyMoveFile(fullProcessedPath, existPath))
+ if (!NFile::NDirectory::MyMoveFile(fullProcessedPath, existPath))
{
UString message = UString(kCantRenameFile) + fullProcessedPath;
RINOK(_extractCallback2->MessageError(message));
@@ -392,6 +378,17 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index, ISequentialOutStre
{
*outStream = NULL;
}
+ if (_crcMode)
+ {
+ _crcStreamSpec = new COutStreamWithCRC;
+ _crcStream = _crcStreamSpec;
+ CMyComPtr<ISequentialOutStream> crcStream = _crcStreamSpec;
+ _crcStreamSpec->SetStream(*outStream);
+ if (*outStream)
+ (*outStream)->Release();
+ *outStream = crcStream.Detach();
+ _crcStreamSpec->Init(true);
+ }
return S_OK;
COM_TRY_END
}
@@ -403,9 +400,13 @@ STDMETHODIMP CArchiveExtractCallback::PrepareOperation(Int32 askExtractMode)
switch (askExtractMode)
{
case NArchive::NExtract::NAskMode::kExtract:
- _extractMode = true;
+ if (_testMode)
+ askExtractMode = NArchive::NExtract::NAskMode::kTest;
+ else
+ _extractMode = true;
+ break;
};
- return _extractCallback2->PrepareOperation(_filePath, _processedFileInfo.IsDir,
+ return _extractCallback2->PrepareOperation(_filePath, _fi.IsDir,
askExtractMode, _isSplit ? &_position: 0);
COM_TRY_END
}
@@ -424,24 +425,35 @@ STDMETHODIMP CArchiveExtractCallback::SetOperationResult(Int32 operationResult)
_outFileStream.Release();
return E_FAIL;
}
- if (_outFileStream != NULL)
+ if (_crcStream)
+ {
+ CrcSum += _crcStreamSpec->GetCRC();
+ _curSize = _crcStreamSpec->GetSize();
+ _curSizeDefined = true;
+ _crcStream.Release();
+ }
+ if (_outFileStream)
{
_outFileStreamSpec->SetTime(
- (WriteCTime && _processedFileInfo.CTimeDefined) ? &_processedFileInfo.CTime : NULL,
- (WriteATime && _processedFileInfo.ATimeDefined) ? &_processedFileInfo.ATime : NULL,
- (WriteMTime && _processedFileInfo.MTimeDefined) ? &_processedFileInfo.MTime : &_utcMTimeDefault);
+ (WriteCTime && _fi.CTimeDefined) ? &_fi.CTime : NULL,
+ (WriteATime && _fi.ATimeDefined) ? &_fi.ATime : NULL,
+ (WriteMTime && _fi.MTimeDefined) ? &_fi.MTime : (_arc->MTimeDefined ? &_arc->MTime : NULL));
_curSize = _outFileStreamSpec->ProcessedSize;
+ _curSizeDefined = true;
RINOK(_outFileStreamSpec->Close());
_outFileStream.Release();
}
- UnpackSize += _curSize;
- if (_processedFileInfo.IsDir)
+ if (!_curSizeDefined)
+ GetUnpackSize();
+ if (_curSizeDefined)
+ UnpackSize += _curSize;
+ if (_fi.IsDir)
NumFolders++;
else
NumFiles++;
- if (_extractMode && _processedFileInfo.AttributesAreDefined)
- NFile::NDirectory::MySetFileAttributes(_diskFilePath, _processedFileInfo.Attributes);
+ if (_extractMode && _fi.AttribDefined)
+ NFile::NDirectory::MySetFileAttributes(_diskFilePath, _fi.Attrib);
RINOK(_extractCallback2->SetOperationResult(operationResult, _encrypted));
return S_OK;
COM_TRY_END
diff --git a/CPP/7zip/UI/Common/ArchiveExtractCallback.h b/CPP/7zip/UI/Common/ArchiveExtractCallback.h
index e895c54b..367e4b07 100755
--- a/CPP/7zip/UI/Common/ArchiveExtractCallback.h
+++ b/CPP/7zip/UI/Common/ArchiveExtractCallback.h
@@ -1,19 +1,23 @@
// ArchiveExtractCallback.h
-#ifndef __ARCHIVEEXTRACTCALLBACK_H
-#define __ARCHIVEEXTRACTCALLBACK_H
+#ifndef __ARCHIVE_EXTRACT_CALLBACK_H
+#define __ARCHIVE_EXTRACT_CALLBACK_H
-#include "../../Archive/IArchive.h"
-#include "IFileExtractCallback.h"
-
-#include "Common/MyString.h"
#include "Common/MyCom.h"
+#include "Common/Wildcard.h"
+
+#include "../../IPassword.h"
#include "../../Common/FileStreams.h"
#include "../../Common/ProgressUtils.h"
-#include "../../IPassword.h"
+
+#include "../../Archive/IArchive.h"
+
+#include "../../Archive/Common/OutStreamWithCRC.h"
#include "ExtractMode.h"
+#include "IFileExtractCallback.h"
+#include "OpenArchive.h"
class CArchiveExtractCallback:
public IArchiveExtractCallback,
@@ -22,22 +26,8 @@ class CArchiveExtractCallback:
public ICompressProgressInfo,
public CMyUnknownImp
{
-public:
- MY_UNKNOWN_IMP2(ICryptoGetTextPassword, ICompressProgressInfo)
- // COM_INTERFACE_ENTRY(IArchiveVolumeExtractCallback)
-
- INTERFACE_IArchiveExtractCallback(;)
-
- STDMETHOD(SetRatioInfo)(const UInt64 *inSize, const UInt64 *outSize);
-
- // IArchiveVolumeExtractCallback
- // STDMETHOD(GetInStream)(const wchar_t *name, ISequentialInStream **inStream);
-
- // ICryptoGetTextPassword
- STDMETHOD(CryptoGetTextPassword)(BSTR *aPassword);
-
-private:
- CMyComPtr<IInArchive> _archiveHandler;
+ const CArc *_arc;
+ const NWildcard::CCensorNode *_wildcardCensor;
CMyComPtr<IFolderArchiveExtractCallback> _extractCallback2;
CMyComPtr<ICompressProgressInfo> _compressProgress;
CMyComPtr<ICryptoGetTextPassword> _cryptoGetTextPassword;
@@ -45,12 +35,11 @@ private:
NExtract::NPathMode::EEnum _pathMode;
NExtract::NOverwriteMode::EEnum _overwriteMode;
+ UString _diskFilePath;
UString _filePath;
UInt64 _position;
bool _isSplit;
- UString _diskFilePath;
-
bool _extractMode;
bool WriteCTime;
@@ -64,29 +53,61 @@ private:
FILETIME CTime;
FILETIME ATime;
FILETIME MTime;
- UInt32 Attributes;
+ UInt32 Attrib;
bool CTimeDefined;
bool ATimeDefined;
bool MTimeDefined;
+ bool AttribDefined;
bool IsDir;
- bool AttributesAreDefined;
- } _processedFileInfo;
+ } _fi;
+ UInt32 _index;
UInt64 _curSize;
+ bool _curSizeDefined;
COutFileStream *_outFileStreamSpec;
CMyComPtr<ISequentialOutStream> _outFileStream;
+
+ COutStreamWithCRC *_crcStreamSpec;
+ CMyComPtr<ISequentialOutStream> _crcStream;
+
UStringVector _removePathParts;
- UString _itemDefaultName;
- FILETIME _utcMTimeDefault;
- UInt32 _attributesDefault;
bool _stdOutMode;
+ bool _testMode;
+ bool _crcMode;
+ bool _multiArchives;
+
+ CMyComPtr<ICompressProgressInfo> _localProgress;
+ UInt64 _packTotal;
+ UInt64 _unpTotal;
void CreateComplexDirectory(const UStringVector &dirPathParts, UString &fullPath);
HRESULT GetTime(int index, PROPID propID, FILETIME &filetime, bool &filetimeIsDefined);
+ HRESULT GetUnpackSize();
+
public:
+
+ CLocalProgress *LocalProgressSpec;
+
+ UInt64 NumFolders;
+ UInt64 NumFiles;
+ UInt64 UnpackSize;
+ UInt32 CrcSum;
+
+ MY_UNKNOWN_IMP2(ICryptoGetTextPassword, ICompressProgressInfo)
+ // COM_INTERFACE_ENTRY(IArchiveVolumeExtractCallback)
+
+ INTERFACE_IArchiveExtractCallback(;)
+
+ STDMETHOD(SetRatioInfo)(const UInt64 *inSize, const UInt64 *outSize);
+
+ // IArchiveVolumeExtractCallback
+ // STDMETHOD(GetInStream)(const wchar_t *name, ISequentialInStream **inStream);
+
+ STDMETHOD(CryptoGetTextPassword)(BSTR *password);
+
CArchiveExtractCallback():
WriteCTime(true),
WriteATime(true),
@@ -97,37 +118,26 @@ public:
_localProgress = LocalProgressSpec;
}
- CLocalProgress *LocalProgressSpec;
- CMyComPtr<ICompressProgressInfo> _localProgress;
- UInt64 _packTotal;
- UInt64 _unpTotal;
-
- bool _multiArchives;
- UInt64 NumFolders;
- UInt64 NumFiles;
- UInt64 UnpackSize;
-
void InitForMulti(bool multiArchives,
NExtract::NPathMode::EEnum pathMode,
NExtract::NOverwriteMode::EEnum overwriteMode)
{
- _multiArchives = multiArchives; NumFolders = NumFiles = UnpackSize = 0;
+ _multiArchives = multiArchives;
_pathMode = pathMode;
_overwriteMode = overwriteMode;
+ NumFolders = NumFiles = UnpackSize = 0;
+ CrcSum = 0;
}
void Init(
- IInArchive *archiveHandler,
+ const NWildcard::CCensorNode *wildcardCensor,
+ const CArc *arc,
IFolderArchiveExtractCallback *extractCallback2,
- bool stdOutMode,
+ bool stdOutMode, bool testMode, bool crcMode,
const UString &directoryPath,
const UStringVector &removePathParts,
- const UString &itemDefaultName,
- const FILETIME &utcMTimeDefault,
- UInt32 attributesDefault,
UInt64 packSize);
- UInt64 _numErrors;
};
#endif
diff --git a/CPP/7zip/UI/Common/ArchiveName.cpp b/CPP/7zip/UI/Common/ArchiveName.cpp
index 9b9a4fe6..c3684def 100755
--- a/CPP/7zip/UI/Common/ArchiveName.cpp
+++ b/CPP/7zip/UI/Common/ArchiveName.cpp
@@ -2,12 +2,14 @@
#include "StdAfx.h"
-#include "Windows/FileFind.h"
#include "Windows/FileDir.h"
+#include "Windows/FileFind.h"
+
+#include "ExtractingFilePath.h"
using namespace NWindows;
-UString CreateArchiveName(const UString &srcName, bool fromPrev, bool keepName)
+static UString CreateArchiveName2(const UString &srcName, bool fromPrev, bool keepName)
{
UString resultName = L"Archive";
if (fromPrev)
@@ -20,7 +22,7 @@ UString CreateArchiveName(const UString &srcName, bool fromPrev, bool keepName)
{
dirPrefix.Delete(dirPrefix.Length() - 1);
NFile::NFind::CFileInfoW fileInfo;
- if (NFile::NFind::FindFile(dirPrefix, fileInfo))
+ if (fileInfo.Find(dirPrefix))
resultName = fileInfo.Name;
}
}
@@ -28,8 +30,9 @@ UString CreateArchiveName(const UString &srcName, bool fromPrev, bool keepName)
else
{
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(srcName, fileInfo))
- return resultName;
+ if (!fileInfo.Find(srcName))
+ // return resultName;
+ return srcName;
resultName = fileInfo.Name;
if (!fileInfo.IsDir() && !keepName)
{
@@ -44,3 +47,8 @@ UString CreateArchiveName(const UString &srcName, bool fromPrev, bool keepName)
}
return resultName;
}
+
+UString CreateArchiveName(const UString &srcName, bool fromPrev, bool keepName)
+{
+ return GetCorrectFsPath(CreateArchiveName2(srcName, fromPrev, keepName));
+}
diff --git a/CPP/7zip/UI/Common/ArchiveOpenCallback.cpp b/CPP/7zip/UI/Common/ArchiveOpenCallback.cpp
index 8f289d1b..7188bcb6 100755
--- a/CPP/7zip/UI/Common/ArchiveOpenCallback.cpp
+++ b/CPP/7zip/UI/Common/ArchiveOpenCallback.cpp
@@ -2,14 +2,15 @@
#include "StdAfx.h"
-#include "ArchiveOpenCallback.h"
-
#include "Common/StringConvert.h"
#include "Common/ComTry.h"
+
#include "Windows/PropVariant.h"
#include "../../Common/FileStreams.h"
+#include "ArchiveOpenCallback.h"
+
using namespace NWindows;
STDMETHODIMP COpenCallbackImp::SetTotal(const UInt64 *files, const UInt64 *bytes)
@@ -91,7 +92,7 @@ STDMETHODIMP COpenCallbackImp::GetStream(const wchar_t *name, IInStream **inStre
}
*inStream = NULL;
UString fullPath = _folderPrefix + name;
- if (!NFile::NFind::FindFile(fullPath, _fileInfo))
+ if (!_fileInfo.Find(fullPath))
return S_FALSE;
if (_fileInfo.IsDir())
return S_FALSE;
diff --git a/CPP/7zip/UI/Common/ArchiveOpenCallback.h b/CPP/7zip/UI/Common/ArchiveOpenCallback.h
index ca445974..c6651e8f 100755
--- a/CPP/7zip/UI/Common/ArchiveOpenCallback.h
+++ b/CPP/7zip/UI/Common/ArchiveOpenCallback.h
@@ -3,8 +3,9 @@
#ifndef __ARCHIVE_OPEN_CALLBACK_H
#define __ARCHIVE_OPEN_CALLBACK_H
-#include "Common/MyString.h"
#include "Common/MyCom.h"
+#include "Common/MyString.h"
+
#include "Windows/FileFind.h"
#ifndef _NO_CRYPTO
@@ -71,6 +72,7 @@ public:
{
_subArchiveMode = true;
_subArchiveName = name;
+ TotalSize = 0;
return S_OK;
}
@@ -86,10 +88,10 @@ public:
UInt64 TotalSize;
COpenCallbackImp(): Callback(NULL) {}
- void Init(const UString &folderPrefix, const UString &fileName)
+ void Init(const UString &folderPrefix, const UString &fileName)
{
_folderPrefix = folderPrefix;
- if (!NWindows::NFile::NFind::FindFile(_folderPrefix + fileName, _fileInfo))
+ if (!_fileInfo.Find(_folderPrefix + fileName))
throw 1;
FileNames.Clear();
_subArchiveMode = false;
diff --git a/CPP/7zip/UI/Common/CompressCall.cpp b/CPP/7zip/UI/Common/CompressCall.cpp
index 3564c950..47f89ed6 100755
--- a/CPP/7zip/UI/Common/CompressCall.cpp
+++ b/CPP/7zip/UI/Common/CompressCall.cpp
@@ -2,20 +2,20 @@
#include "StdAfx.h"
-#include "CompressCall.h"
-
-#include "Common/Random.h"
#include "Common/IntToString.h"
#include "Common/MyCom.h"
+#include "Common/Random.h"
#include "Common/StringConvert.h"
-#include "Windows/Synchronization.h"
-#include "Windows/FileMapping.h"
#include "Windows/FileDir.h"
+#include "Windows/FileMapping.h"
+#include "Windows/Synchronization.h"
#include "../FileManager/ProgramLocation.h"
#include "../FileManager/RegistryUtils.h"
+#include "CompressCall.h"
+
#ifndef _UNICODE
extern bool g_IsNT;
#endif _UNICODE
@@ -122,8 +122,8 @@ static HRESULT CreateTempEvent(const wchar_t *name,
for (;;)
{
int number = random.Generate();
- wchar_t temp[32];
- ConvertUInt64ToString((UInt32)number, temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString((UInt32)number, temp);
eventName = name;
eventName += temp;
RINOK(event.CreateWithName(false, GetSystemString(eventName)));
@@ -151,8 +151,8 @@ static HRESULT CreateMap(const UStringVector &names,
for (;;)
{
int number = random.Generate();
- wchar_t temp[32];
- ConvertUInt64ToString(UInt32(number), temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(UInt32(number), temp);
mappingName = id;
mappingName += L"Mapping";
mappingName += temp;
@@ -169,8 +169,8 @@ static HRESULT CreateMap(const UStringVector &names,
params += mappingName;
params += L":";
- wchar_t string[10];
- ConvertUInt64ToString(totalSize, string);
+ wchar_t string[16];
+ ConvertUInt32ToString(totalSize, string);
params += string;
params += L":";
@@ -231,8 +231,8 @@ HRESULT CompressFiles(
for (;;)
{
int number = random.Generate();
- wchar_t temp[32];
- ConvertUInt64ToString(UInt32(number), temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(UInt32(number), temp);
mappingName = L"7zCompressMapping";
mappingName += temp;
if (!fileMapping.Create(INVALID_HANDLE_VALUE, NULL,
@@ -252,8 +252,8 @@ HRESULT CompressFiles(
params += mappingName;
params += L":";
- wchar_t string[10];
- ConvertUInt64ToString(totalSize, string);
+ wchar_t string[16];
+ ConvertUInt32ToString(totalSize, string);
params += string;
params += L":";
diff --git a/CPP/7zip/UI/Common/DirItem.h b/CPP/7zip/UI/Common/DirItem.h
index 0f289483..29cc60d9 100755
--- a/CPP/7zip/UI/Common/DirItem.h
+++ b/CPP/7zip/UI/Common/DirItem.h
@@ -58,11 +58,12 @@ struct CArcItem
UString Name;
bool IsDir;
bool SizeDefined;
+ bool MTimeDefined;
bool Censored;
UInt32 IndexInServer;
int TimeType;
- CArcItem(): IsDir(false), SizeDefined(false), Censored(false), TimeType(-1) {}
+ CArcItem(): IsDir(false), SizeDefined(false), MTimeDefined(false), Censored(false), TimeType(-1) {}
};
#endif
diff --git a/CPP/7zip/UI/Common/EnumDirItems.cpp b/CPP/7zip/UI/Common/EnumDirItems.cpp
index b83edf2a..ba03ea35 100755
--- a/CPP/7zip/UI/Common/EnumDirItems.cpp
+++ b/CPP/7zip/UI/Common/EnumDirItems.cpp
@@ -2,12 +2,6 @@
#include "StdAfx.h"
-#include <stdio.h>
-
-#include "Common/StringConvert.h"
-#include "Common/Wildcard.h"
-#include "Common/MyCom.h"
-
#include "EnumDirItems.h"
using namespace NWindows;
@@ -122,7 +116,7 @@ void CDirItems::EnumerateDirItems2(const UString &phyPrefix, const UString &logP
const UString &filePath = filePaths[i];
NFind::CFileInfoW fi;
const UString phyPath = phyPrefix + filePath;
- if (!NFind::FindFile(phyPath, fi))
+ if (!fi.Find(phyPath))
{
errorCodes.Add(::GetLastError());
errorPaths.Add(phyPath);
@@ -218,7 +212,7 @@ static HRESULT EnumerateDirItems(const NWildcard::CCensorNode &curNode,
const UString &name = item.PathParts.Front();
const UString fullPath = phyPrefix + name;
NFind::CFileInfoW fi;
- if (!NFind::FindFile(fullPath, fi))
+ if (!fi.Find(fullPath))
{
errorCodes.Add(::GetLastError());
errorPaths.Add(fullPath);
@@ -268,7 +262,7 @@ static HRESULT EnumerateDirItems(const NWildcard::CCensorNode &curNode,
const NWildcard::CCensorNode &nextNode = curNode.SubNodes[i];
const UString fullPath = phyPrefix + nextNode.Name;
NFind::CFileInfoW fi;
- if (!NFind::FindFile(fullPath, fi))
+ if (!fi.Find(fullPath))
{
if (!nextNode.AreThereIncludeItems())
continue;
diff --git a/CPP/7zip/UI/Common/Extract.cpp b/CPP/7zip/UI/Common/Extract.cpp
index 3ac497f4..93329091 100755
--- a/CPP/7zip/UI/Common/Extract.cpp
+++ b/CPP/7zip/UI/Common/Extract.cpp
@@ -2,55 +2,65 @@
#include "StdAfx.h"
-#include "Extract.h"
+#include <stdio.h>
-#include "Windows/Defs.h"
#include "Windows/FileDir.h"
+#include "Windows/PropVariant.h"
+#include "Windows/PropVariantConversions.h"
+
+#include "../Common/ExtractingFilePath.h"
-#include "OpenArchive.h"
+#include "Extract.h"
#include "SetProperties.h"
using namespace NWindows;
static HRESULT DecompressArchive(
- IInArchive *archive,
+ const CArc &arc,
UInt64 packSize,
const NWildcard::CCensorNode &wildcardCensor,
const CExtractOptions &options,
IExtractCallbackUI *callback,
CArchiveExtractCallback *extractCallbackSpec,
- UString &errorMessage)
+ UString &errorMessage,
+ UInt64 &stdInProcessed)
{
+ stdInProcessed = 0;
+ IInArchive *archive = arc.Archive;
CRecordVector<UInt32> realIndices;
- UInt32 numItems;
- RINOK(archive->GetNumberOfItems(&numItems));
-
- for(UInt32 i = 0; i < numItems; i++)
- {
- UString filePath;
- RINOK(GetArchiveItemPath(archive, i, options.DefaultItemName, filePath));
- bool isFolder;
- RINOK(IsArchiveItemFolder(archive, i, isFolder));
- if (!wildcardCensor.CheckPath(filePath, !isFolder))
- continue;
- realIndices.Add(i);
- }
- if (realIndices.Size() == 0)
+ if (!options.StdInMode)
{
- callback->ThereAreNoFiles();
- return S_OK;
+ UInt32 numItems;
+ RINOK(archive->GetNumberOfItems(&numItems));
+
+ for (UInt32 i = 0; i < numItems; i++)
+ {
+ UString filePath;
+ RINOK(arc.GetItemPath(i, filePath));
+ bool isFolder;
+ RINOK(IsArchiveItemFolder(archive, i, isFolder));
+ if (!wildcardCensor.CheckPath(filePath, !isFolder))
+ continue;
+ realIndices.Add(i);
+ }
+ if (realIndices.Size() == 0)
+ {
+ callback->ThereAreNoFiles();
+ return S_OK;
+ }
}
UStringVector removePathParts;
UString outDir = options.OutputDir;
- outDir.Replace(L"*", options.DefaultItemName);
+ outDir.Replace(L"*", GetCorrectFsPath(arc.DefaultName));
#ifdef _WIN32
outDir.TrimRight();
+ outDir = GetCorrectFullFsPath(outDir);
#endif
- if(!outDir.IsEmpty())
- if(!NFile::NDirectory::CreateComplexDirectory(outDir))
+ if (!outDir.IsEmpty())
+ if (!NFile::NDirectory::CreateComplexDirectory(outDir))
{
HRESULT res = ::GetLastError();
if (res == S_OK)
@@ -60,91 +70,108 @@ static HRESULT DecompressArchive(
}
extractCallbackSpec->Init(
- archive,
+ options.StdInMode ? &wildcardCensor : NULL,
+ &arc,
callback,
- options.StdOutMode,
+ options.StdOutMode, options.TestMode, options.CalcCrc,
outDir,
removePathParts,
- options.DefaultItemName,
- options.ArchiveFileInfo.MTime,
- options.ArchiveFileInfo.Attrib,
packSize);
#ifdef COMPRESS_MT
RINOK(SetProperties(archive, options.Properties));
#endif
- HRESULT result = archive->Extract(&realIndices.Front(),
- realIndices.Size(), options.TestMode? 1: 0, extractCallbackSpec);
+ HRESULT result;
+ Int32 testMode = (options.TestMode && !options.CalcCrc) ? 1: 0;
+ if (options.StdInMode)
+ {
+ result = archive->Extract(NULL, (UInt32)(Int32)-1, testMode, extractCallbackSpec);
+ NCOM::CPropVariant prop;
+ if (archive->GetArchiveProperty(kpidPhySize, &prop) == S_OK)
+ if (prop.vt == VT_UI8 || prop.vt == VT_UI4)
+ stdInProcessed = ConvertPropVariantToUInt64(prop);
+ }
+ else
+ result = archive->Extract(&realIndices.Front(), realIndices.Size(), testMode, extractCallbackSpec);
return callback->ExtractResult(result);
}
HRESULT DecompressArchives(
CCodecs *codecs, const CIntVector &formatIndices,
- UStringVector &archivePaths, UStringVector &archivePathsFull,
+ UStringVector &arcPaths, UStringVector &arcPathsFull,
const NWildcard::CCensorNode &wildcardCensor,
- const CExtractOptions &optionsSpec,
+ const CExtractOptions &options,
IOpenCallbackUI *openCallback,
IExtractCallbackUI *extractCallback,
UString &errorMessage,
CDecompressStat &stat)
{
stat.Clear();
- CExtractOptions options = optionsSpec;
int i;
UInt64 totalPackSize = 0;
CRecordVector<UInt64> archiveSizes;
- for (i = 0; i < archivePaths.Size(); i++)
+
+ int numArcs = options.StdInMode ? 1 : arcPaths.Size();
+
+ for (i = 0; i < numArcs; i++)
{
- const UString &archivePath = archivePaths[i];
NFile::NFind::CFileInfoW fi;
- if (!NFile::NFind::FindFile(archivePath, fi))
- throw "there is no such archive";
- if (fi.IsDir())
- throw "can't decompress folder";
+ fi.Size = 0;
+ if (!options.StdInMode)
+ {
+ const UString &arcPath = arcPaths[i];
+ if (!fi.Find(arcPath))
+ throw "there is no such archive";
+ if (fi.IsDir())
+ throw "can't decompress folder";
+ }
archiveSizes.Add(fi.Size);
totalPackSize += fi.Size;
}
CArchiveExtractCallback *extractCallbackSpec = new CArchiveExtractCallback;
CMyComPtr<IArchiveExtractCallback> ec(extractCallbackSpec);
- bool multi = (archivePaths.Size() > 1);
+ bool multi = (numArcs > 1);
extractCallbackSpec->InitForMulti(multi, options.PathMode, options.OverwriteMode);
if (multi)
{
RINOK(extractCallback->SetTotal(totalPackSize));
}
- for (i = 0; i < archivePaths.Size(); i++)
+ for (i = 0; i < numArcs; i++)
{
- const UString &archivePath = archivePaths[i];
+ const UString &arcPath = arcPaths[i];
NFile::NFind::CFileInfoW fi;
- if (!NFile::NFind::FindFile(archivePath, fi))
- throw "there is no such archive";
-
- if (fi.IsDir())
- throw "there is no such archive";
-
- options.ArchiveFileInfo = fi;
+ if (options.StdInMode)
+ {
+ fi.Size = 0;
+ fi.Attrib = 0;
+ }
+ else
+ {
+ if (!fi.Find(arcPath) || fi.IsDir())
+ throw "there is no such archive";
+ }
#ifndef _NO_CRYPTO
openCallback->Open_ClearPasswordWasAskedFlag();
#endif
- RINOK(extractCallback->BeforeOpen(archivePath));
+ RINOK(extractCallback->BeforeOpen(arcPath));
CArchiveLink archiveLink;
CIntVector formatIndices2 = formatIndices;
#ifndef _SFX
if (formatIndices.IsEmpty())
{
- int pos = archivePath.ReverseFind(L'.');
+ int pos = arcPath.ReverseFind(L'.');
if (pos >= 0)
{
- UString s = archivePath.Mid(pos + 1);
+ UString s = arcPath.Mid(pos + 1);
int index = codecs->FindFormatForExtension(s);
if (index >= 0 && s == L"001")
{
- s = archivePath.Left(pos);
+ s = arcPath.Left(pos);
pos = s.ReverseFind(L'.');
if (pos >= 0)
{
@@ -159,7 +186,7 @@ HRESULT DecompressArchives(
}
}
#endif
- HRESULT result = MyOpenArchive(codecs, formatIndices2, archivePath, archiveLink, openCallback);
+ HRESULT result = archiveLink.Open2(codecs, formatIndices2, options.StdInMode, NULL, arcPath, openCallback);
if (result == E_ABORT)
return result;
@@ -168,19 +195,21 @@ HRESULT DecompressArchives(
crypted = openCallback->Open_WasPasswordAsked();
#endif
- RINOK(extractCallback->OpenResult(archivePath, result, crypted));
+ RINOK(extractCallback->OpenResult(arcPath, result, crypted));
if (result != S_OK)
continue;
+ if (!options.StdInMode)
for (int v = 0; v < archiveLink.VolumePaths.Size(); v++)
{
- int index = archivePathsFull.FindInSorted(archiveLink.VolumePaths[v]);
+ int index = arcPathsFull.FindInSorted(archiveLink.VolumePaths[v]);
if (index >= 0 && index > i)
{
- archivePaths.Delete(index);
- archivePathsFull.Delete(index);
+ arcPaths.Delete(index);
+ arcPathsFull.Delete(index);
totalPackSize -= archiveSizes[index];
archiveSizes.Delete(index);
+ numArcs = arcPaths.Size();
}
}
if (archiveLink.VolumePaths.Size() != 0)
@@ -198,13 +227,17 @@ HRESULT DecompressArchives(
}
#endif
- options.DefaultItemName = archiveLink.GetDefaultItemName();
- RINOK(DecompressArchive(
- archiveLink.GetArchive(),
+ CArc &arc = archiveLink.Arcs.Back();
+ arc.MTimeDefined = (!options.StdInMode && !fi.IsDevice);
+ arc.MTime = fi.MTime;
+
+ UInt64 packProcessed;
+ RINOK(DecompressArchive(arc,
fi.Size + archiveLink.VolumesSize,
- wildcardCensor, options, extractCallback, extractCallbackSpec, errorMessage));
- extractCallbackSpec->LocalProgressSpec->InSize += fi.Size +
- archiveLink.VolumesSize;
+ wildcardCensor, options, extractCallback, extractCallbackSpec, errorMessage, packProcessed));
+ if (!options.StdInMode)
+ packProcessed = fi.Size + archiveLink.VolumesSize;
+ extractCallbackSpec->LocalProgressSpec->InSize += packProcessed;
extractCallbackSpec->LocalProgressSpec->OutSize = extractCallbackSpec->UnpackSize;
if (!errorMessage.IsEmpty())
return E_FAIL;
@@ -212,7 +245,9 @@ HRESULT DecompressArchives(
stat.NumFolders = extractCallbackSpec->NumFolders;
stat.NumFiles = extractCallbackSpec->NumFiles;
stat.UnpackSize = extractCallbackSpec->UnpackSize;
- stat.NumArchives = archivePaths.Size();
+ stat.CrcSum = extractCallbackSpec->CrcSum;
+
+ stat.NumArchives = arcPaths.Size();
stat.PackSize = extractCallbackSpec->LocalProgressSpec->InSize;
return S_OK;
}
diff --git a/CPP/7zip/UI/Common/Extract.h b/CPP/7zip/UI/Common/Extract.h
index 37add18b..442dd2b0 100755
--- a/CPP/7zip/UI/Common/Extract.h
+++ b/CPP/7zip/UI/Common/Extract.h
@@ -3,7 +3,6 @@
#ifndef __EXTRACT_H
#define __EXTRACT_H
-#include "Common/Wildcard.h"
#include "Windows/FileFind.h"
#include "../../Archive/IArchive.h"
@@ -15,17 +14,16 @@
#include "../Common/LoadCodecs.h"
-class CExtractOptions
+struct CExtractOptions
{
-public:
+ bool StdInMode;
bool StdOutMode;
+ bool YesToAll;
bool TestMode;
+ bool CalcCrc;
NExtract::NPathMode::EEnum PathMode;
-
+ NExtract::NOverwriteMode::EEnum OverwriteMode;
UString OutputDir;
- bool YesToAll;
- UString DefaultItemName;
- NWindows::NFile::NFind::CFileInfoW ArchiveFileInfo;
// bool ShowDialog;
// bool PasswordEnabled;
@@ -34,24 +32,19 @@ public:
CObjectVector<CProperty> Properties;
#endif
- NExtract::NOverwriteMode::EEnum OverwriteMode;
-
#ifdef EXTERNAL_CODECS
CCodecs *Codecs;
#endif
CExtractOptions():
+ StdInMode(false),
StdOutMode(false),
YesToAll(false),
TestMode(false),
+ CalcCrc(false),
PathMode(NExtract::NPathMode::kFullPathnames),
OverwriteMode(NExtract::NOverwriteMode::kAskBefore)
{}
-
- /*
- bool FullPathMode() const { return (ExtractMode == NExtractMode::kTest) ||
- (ExtractMode == NExtractMode::kFullPath); }
- */
};
struct CDecompressStat
@@ -61,7 +54,13 @@ struct CDecompressStat
UInt64 PackSize;
UInt64 NumFolders;
UInt64 NumFiles;
- void Clear() { NumArchives = PackSize = UnpackSize = NumFolders = NumFiles = 0; }
+ UInt32 CrcSum;
+
+ void Clear()
+ {
+ NumArchives = UnpackSize = PackSize = NumFolders = NumFiles = 0;
+ CrcSum = 0;
+ }
};
HRESULT DecompressArchives(
diff --git a/CPP/7zip/UI/Common/ExtractingFilePath.cpp b/CPP/7zip/UI/Common/ExtractingFilePath.cpp
index 5de388dd..67a58372 100755
--- a/CPP/7zip/UI/Common/ExtractingFilePath.cpp
+++ b/CPP/7zip/UI/Common/ExtractingFilePath.cpp
@@ -1,6 +1,9 @@
// ExtractingFilePath.cpp
#include "StdAfx.h"
+
+#include "Common/Wildcard.h"
+
#include "ExtractingFilePath.h"
static UString ReplaceIncorrectChars(const UString &s)
@@ -15,6 +18,8 @@ static UString ReplaceIncorrectChars(const UString &s)
res += c;
}
res.TrimRight();
+ while (!res.IsEmpty() && res[res.Length() - 1] == '.')
+ res.Delete(res.Length() - 1);
return res;
#else
return s;
@@ -95,3 +100,41 @@ void MakeCorrectPath(UStringVector &pathParts)
}
}
+UString MakePathNameFromParts(const UStringVector &parts)
+{
+ UString result;
+ for (int i = 0; i < parts.Size(); i++)
+ {
+ if (i != 0)
+ result += WCHAR_PATH_SEPARATOR;
+ result += parts[i];
+ }
+ return result;
+}
+
+UString GetCorrectFsPath(const UString &path)
+{
+ UString res = GetCorrectFileName(path);
+ #ifdef _WIN32
+ if (!IsSupportedName(res))
+ res = (UString)L"_" + res;
+ #endif
+ return res;
+}
+
+UString GetCorrectFullFsPath(const UString &path)
+{
+ UStringVector parts;
+ SplitPathToParts(path, parts);
+ for (int i = 0; i < parts.Size(); i++)
+ {
+ UString &s = parts[i];
+ #ifdef _WIN32
+ while (!s.IsEmpty() && s[s.Length() - 1] == '.')
+ s.Delete(s.Length() - 1);
+ if (!IsSupportedName(s))
+ s = (UString)L"_" + s;
+ #endif
+ }
+ return MakePathNameFromParts(parts);
+}
diff --git a/CPP/7zip/UI/Common/ExtractingFilePath.h b/CPP/7zip/UI/Common/ExtractingFilePath.h
index a86a6a9b..da28bfc2 100755
--- a/CPP/7zip/UI/Common/ExtractingFilePath.h
+++ b/CPP/7zip/UI/Common/ExtractingFilePath.h
@@ -1,10 +1,13 @@
// ExtractingFilePath.h
-#ifndef __EXTRACTINGFILEPATH_H
-#define __EXTRACTINGFILEPATH_H
+#ifndef __EXTRACTING_FILE_PATH_H
+#define __EXTRACTING_FILE_PATH_H
#include "Common/MyString.h"
+UString MakePathNameFromParts(const UStringVector &parts);
void MakeCorrectPath(UStringVector &pathParts);
+UString GetCorrectFsPath(const UString &path);
+UString GetCorrectFullFsPath(const UString &path);
#endif
diff --git a/CPP/7zip/UI/Common/LoadCodecs.cpp b/CPP/7zip/UI/Common/LoadCodecs.cpp
index 4b5639ee..dac8c4d2 100755
--- a/CPP/7zip/UI/Common/LoadCodecs.cpp
+++ b/CPP/7zip/UI/Common/LoadCodecs.cpp
@@ -69,22 +69,17 @@ static bool ReadPathFromRegistry(HKEY baseKey, CSysString &path)
CSysString GetBaseFolderPrefixFromRegistry()
{
CSysString moduleFolderPrefix = GetLibraryFolderPrefix();
- NFind::CFileInfo fi;
- if (NFind::FindFile(moduleFolderPrefix + kMainDll, fi))
- if (!fi.IsDir())
- return moduleFolderPrefix;
- if (NFind::FindFile(moduleFolderPrefix + kCodecsFolderName, fi))
- if (fi.IsDir())
- return moduleFolderPrefix;
- if (NFind::FindFile(moduleFolderPrefix + kFormatsFolderName, fi))
- if (fi.IsDir())
- return moduleFolderPrefix;
#ifdef _WIN32
- CSysString path;
- if (ReadPathFromRegistry(HKEY_CURRENT_USER, path))
- return path;
- if (ReadPathFromRegistry(HKEY_LOCAL_MACHINE, path))
- return path;
+ if (!NFind::DoesFileExist(moduleFolderPrefix + kMainDll) &&
+ !NFind::DoesDirExist(moduleFolderPrefix + kCodecsFolderName) &&
+ !NFind::DoesDirExist(moduleFolderPrefix + kFormatsFolderName))
+ {
+ CSysString path;
+ if (ReadPathFromRegistry(HKEY_CURRENT_USER, path))
+ return path;
+ if (ReadPathFromRegistry(HKEY_LOCAL_MACHINE, path))
+ return path;
+ }
#endif
return moduleFolderPrefix;
}
@@ -181,7 +176,7 @@ static HRESULT ReadStringProp(
#endif
-static const unsigned int kNumArcsMax = 32;
+static const unsigned int kNumArcsMax = 48;
static unsigned int g_NumArcs = 0;
static const CArcInfo *g_Arcs[kNumArcsMax];
void RegisterArc(const CArcInfo *arcInfo)
@@ -457,9 +452,7 @@ int CCodecs::FindFormatForArchiveName(const UString &arcPath) const
const CArcInfoEx &arc = Formats[i];
if (!arc.UpdateEnabled)
continue;
- // if (arc.FindExtension(ext) >= 0)
- UString mainExt = arc.GetMainExt();
- if (!mainExt.IsEmpty() && ext.CompareNoCase(mainExt) == 0)
+ if (arc.FindExtension(ext) >= 0)
return i;
}
return -1;
diff --git a/CPP/7zip/UI/Common/OpenArchive.cpp b/CPP/7zip/UI/Common/OpenArchive.cpp
index 364ddff5..ec9f9a45 100755
--- a/CPP/7zip/UI/Common/OpenArchive.cpp
+++ b/CPP/7zip/UI/Common/OpenArchive.cpp
@@ -2,45 +2,56 @@
#include "StdAfx.h"
-#include "OpenArchive.h"
-
#include "Common/Wildcard.h"
-#include "Windows/FileName.h"
#include "Windows/FileDir.h"
-#include "Windows/Defs.h"
#include "Windows/PropVariant.h"
#include "../../Common/FileStreams.h"
#include "../../Common/StreamUtils.h"
-#include "Common/StringConvert.h"
-
#include "DefaultName.h"
+#include "OpenArchive.h"
using namespace NWindows;
-HRESULT GetArchiveItemPath(IInArchive *archive, UInt32 index, UString &result)
+// Static-SFX (for Linux) can be big.
+const UInt64 kMaxCheckStartPosition = 1 << 22;
+
+HRESULT GetArchiveItemBoolProp(IInArchive *archive, UInt32 index, PROPID propID, bool &result)
{
NCOM::CPropVariant prop;
- RINOK(archive->GetProperty(index, kpidPath, &prop));
- if(prop.vt == VT_BSTR)
- result = prop.bstrVal;
- else if (prop.vt == VT_EMPTY)
- result.Empty();
- else
+ result = false;
+ RINOK(archive->GetProperty(index, propID, &prop));
+ if (prop.vt == VT_BOOL)
+ result = VARIANT_BOOLToBool(prop.boolVal);
+ else if (prop.vt != VT_EMPTY)
return E_FAIL;
return S_OK;
}
-HRESULT GetArchiveItemPath(IInArchive *archive, UInt32 index, const UString &defaultName, UString &result)
+HRESULT IsArchiveItemFolder(IInArchive *archive, UInt32 index, bool &result)
{
- RINOK(GetArchiveItemPath(archive, index, result));
+ return GetArchiveItemBoolProp(archive, index, kpidIsDir, result);
+}
+
+HRESULT CArc::GetItemPath(UInt32 index, UString &result) const
+{
+ {
+ NCOM::CPropVariant prop;
+ RINOK(Archive->GetProperty(index, kpidPath, &prop));
+ if (prop.vt == VT_BSTR)
+ result = prop.bstrVal;
+ else if (prop.vt == VT_EMPTY)
+ result.Empty();
+ else
+ return E_FAIL;
+ }
if (result.IsEmpty())
{
- result = defaultName;
+ result = DefaultName;
NCOM::CPropVariant prop;
- RINOK(archive->GetProperty(index, kpidExtension, &prop));
+ RINOK(Archive->GetProperty(index, kpidExtension, &prop));
if (prop.vt == VT_BSTR)
{
result += L'.';
@@ -52,54 +63,27 @@ HRESULT GetArchiveItemPath(IInArchive *archive, UInt32 index, const UString &def
return S_OK;
}
-HRESULT GetArchiveItemFileTime(IInArchive *archive, UInt32 index,
- const FILETIME &defaultFileTime, FILETIME &fileTime)
+HRESULT CArc::GetItemMTime(UInt32 index, FILETIME &ft, bool &defined) const
{
NCOM::CPropVariant prop;
- RINOK(archive->GetProperty(index, kpidMTime, &prop));
+ defined = false;
+ ft.dwHighDateTime = ft.dwLowDateTime = 0;
+ RINOK(Archive->GetProperty(index, kpidMTime, &prop));
if (prop.vt == VT_FILETIME)
- fileTime = prop.filetime;
- else if (prop.vt == VT_EMPTY)
- fileTime = defaultFileTime;
- else
- return E_FAIL;
- return S_OK;
-}
-
-HRESULT IsArchiveItemProp(IInArchive *archive, UInt32 index, PROPID propID, bool &result)
-{
- NCOM::CPropVariant prop;
- RINOK(archive->GetProperty(index, propID, &prop));
- if(prop.vt == VT_BOOL)
- result = VARIANT_BOOLToBool(prop.boolVal);
- else if (prop.vt == VT_EMPTY)
- result = false;
- else
+ {
+ ft = prop.filetime;
+ defined = true;
+ }
+ else if (prop.vt != VT_EMPTY)
return E_FAIL;
+ else if (MTimeDefined)
+ {
+ ft = MTime;
+ defined = true;
+ }
return S_OK;
}
-HRESULT IsArchiveItemFolder(IInArchive *archive, UInt32 index, bool &result)
-{
- return IsArchiveItemProp(archive, index, kpidIsDir, result);
-}
-
-HRESULT IsArchiveItemAnti(IInArchive *archive, UInt32 index, bool &result)
-{
- return IsArchiveItemProp(archive, index, kpidIsAnti, result);
-}
-
-// Static-SFX (for Linux) can be big.
-const UInt64 kMaxCheckStartPosition = 1 << 22;
-
-HRESULT ReOpenArchive(IInArchive *archive, const UString &fileName, IArchiveOpenCallback *openArchiveCallback)
-{
- CInFileStream *inStreamSpec = new CInFileStream;
- CMyComPtr<IInStream> inStream(inStreamSpec);
- inStreamSpec->Open(fileName);
- return archive->Open(inStream, &kMaxCheckStartPosition, openArchiveCallback);
-}
-
#ifndef _SFX
static inline bool TestSignature(const Byte *p1, const Byte *p2, size_t size)
{
@@ -110,17 +94,15 @@ static inline bool TestSignature(const Byte *p1, const Byte *p2, size_t size)
}
#endif
-HRESULT OpenArchive(
+HRESULT CArc::OpenStream(
CCodecs *codecs,
- int arcTypeIndex,
- IInStream *inStream,
- const UString &fileName,
- IInArchive **archiveResult,
- int &formatIndex,
- UString &defaultItemName,
- IArchiveOpenCallback *openArchiveCallback)
+ int formatIndex,
+ IInStream *stream,
+ ISequentialInStream *seqStream,
+ IArchiveOpenCallback *callback)
{
- *archiveResult = NULL;
+ Archive.Release();
+ const UString fileName = ExtractFileNameFromPath(Path);
UString extension;
{
int dotPos = fileName.ReverseFind(L'.');
@@ -128,8 +110,8 @@ HRESULT OpenArchive(
extension = fileName.Mid(dotPos + 1);
}
CIntVector orderIndices;
- if (arcTypeIndex >= 0)
- orderIndices.Add(arcTypeIndex);
+ if (formatIndex >= 0)
+ orderIndices.Add(formatIndex);
else
{
@@ -141,16 +123,23 @@ HRESULT OpenArchive(
else
orderIndices.Add(i);
+ if (!stream)
+ {
+ if (numFinded != 1)
+ return E_NOTIMPL;
+ orderIndices.DeleteFrom(1);
+ }
+
#ifndef _SFX
- if (numFinded != 1)
+ if (numFinded == 0)
{
CIntVector orderIndices2;
CByteBuffer byteBuffer;
const size_t kBufferSize = (1 << 21);
byteBuffer.SetCapacity(kBufferSize);
- RINOK(inStream->Seek(0, STREAM_SEEK_SET, NULL));
+ RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
size_t processedSize = kBufferSize;
- RINOK(ReadStream(inStream, byteBuffer, &processedSize));
+ RINOK(ReadStream(stream, byteBuffer, &processedSize));
if (processedSize == 0)
return S_FALSE;
@@ -206,24 +195,6 @@ HRESULT OpenArchive(
orderIndices2.Add(val);
}
orderIndices = orderIndices2;
-
- if (orderIndices.Size() >= 2)
- {
- int isoIndex = codecs->FindFormatForArchiveType(L"iso");
- int udfIndex = codecs->FindFormatForArchiveType(L"udf");
- int iIso = -1;
- int iUdf = -1;
- for (int i = 0; i < orderIndices.Size(); i++)
- {
- if (orderIndices[i] == isoIndex) iIso = i;
- if (orderIndices[i] == udfIndex) iUdf = i;
- }
- if (iUdf == iIso + 1)
- {
- orderIndices[iUdf] = isoIndex;
- orderIndices[iIso] = udfIndex;
- }
- }
}
else if (extension == L"000" || extension == L"001")
{
@@ -231,9 +202,9 @@ HRESULT OpenArchive(
const size_t kBufferSize = (1 << 10);
byteBuffer.SetCapacity(kBufferSize);
Byte *buffer = byteBuffer;
- RINOK(inStream->Seek(0, STREAM_SEEK_SET, NULL));
+ RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
size_t processedSize = kBufferSize;
- RINOK(ReadStream(inStream, buffer, &processedSize));
+ RINOK(ReadStream(stream, buffer, &processedSize));
if (processedSize >= 16)
{
Byte kRarHeader[] = {0x52 , 0x61, 0x72, 0x21, 0x1a, 0x07, 0x00};
@@ -252,17 +223,37 @@ HRESULT OpenArchive(
}
}
}
+ if (orderIndices.Size() >= 2)
+ {
+ int isoIndex = codecs->FindFormatForArchiveType(L"iso");
+ int udfIndex = codecs->FindFormatForArchiveType(L"udf");
+ int iIso = -1;
+ int iUdf = -1;
+ for (int i = 0; i < orderIndices.Size(); i++)
+ {
+ if (orderIndices[i] == isoIndex) iIso = i;
+ if (orderIndices[i] == udfIndex) iUdf = i;
+ }
+ if (iUdf > iIso && iIso >= 0)
+ {
+ orderIndices[iUdf] = isoIndex;
+ orderIndices[iIso] = udfIndex;
+ }
+ }
+
#endif
}
- for(int i = 0; i < orderIndices.Size(); i++)
+ for (int i = 0; i < orderIndices.Size(); i++)
{
- inStream->Seek(0, STREAM_SEEK_SET, NULL);
-
+ if (stream)
+ {
+ RINOK(stream->Seek(0, STREAM_SEEK_SET, NULL));
+ }
CMyComPtr<IInArchive> archive;
- formatIndex = orderIndices[i];
- RINOK(codecs->CreateInArchive(formatIndex, archive));
+ FormatIndex = orderIndices[i];
+ RINOK(codecs->CreateInArchive(FormatIndex, archive));
if (!archive)
continue;
@@ -277,274 +268,239 @@ HRESULT OpenArchive(
}
#endif
- HRESULT result = archive->Open(inStream, &kMaxCheckStartPosition, openArchiveCallback);
+ // OutputDebugStringW(codecs->Formats[FormatIndex].Name);
+
+ HRESULT result;
+ if (stream)
+ result = archive->Open(stream, &kMaxCheckStartPosition, callback);
+ else
+ {
+ CMyComPtr<IArchiveOpenSeq> openSeq;
+ archive.QueryInterface(IID_IArchiveOpenSeq, (void **)&openSeq);
+ if (!openSeq)
+ return E_NOTIMPL;
+ result = openSeq->OpenSeq(seqStream);
+ }
+
if (result == S_FALSE)
continue;
RINOK(result);
- *archiveResult = archive.Detach();
- const CArcInfoEx &format = codecs->Formats[formatIndex];
+
+ Archive = archive;
+ const CArcInfoEx &format = codecs->Formats[FormatIndex];
if (format.Exts.Size() == 0)
- {
- defaultItemName = GetDefaultName2(fileName, L"", L"");
- }
+ DefaultName = GetDefaultName2(fileName, L"", L"");
else
{
int subExtIndex = format.FindExtension(extension);
if (subExtIndex < 0)
subExtIndex = 0;
- defaultItemName = GetDefaultName2(fileName,
- format.Exts[subExtIndex].Ext,
- format.Exts[subExtIndex].AddExt);
+ const CArcExtInfo &extInfo = format.Exts[subExtIndex];
+ DefaultName = GetDefaultName2(fileName, extInfo.Ext, extInfo.AddExt);
}
return S_OK;
}
return S_FALSE;
}
-HRESULT OpenArchive(
+HRESULT CArc::OpenStreamOrFile(
CCodecs *codecs,
- int arcTypeIndex,
- const UString &filePath,
- IInArchive **archiveResult,
- int &formatIndex,
- UString &defaultItemName,
- IArchiveOpenCallback *openArchiveCallback)
+ int formatIndex,
+ bool stdInMode,
+ IInStream *stream,
+ IArchiveOpenCallback *callback)
{
- CInFileStream *inStreamSpec = new CInFileStream;
- CMyComPtr<IInStream> inStream(inStreamSpec);
- if (!inStreamSpec->Open(filePath))
- return GetLastError();
- return OpenArchive(codecs, arcTypeIndex, inStream, ExtractFileNameFromPath(filePath),
- archiveResult, formatIndex,
- defaultItemName, openArchiveCallback);
+ CMyComPtr<IInStream> fileStream;
+ CMyComPtr<ISequentialInStream> seqStream;
+ if (stdInMode)
+ seqStream = new CStdInFileStream;
+ else if (!stream)
+ {
+ CInFileStream *fileStreamSpec = new CInFileStream;
+ fileStream = fileStreamSpec;
+ if (!fileStreamSpec->Open(Path))
+ return GetLastError();
+ stream = fileStream;
+ }
+
+ return OpenStream(codecs, formatIndex, stream, seqStream, callback);
}
-static void MakeDefaultName(UString &name)
+HRESULT CArchiveLink::Close()
{
- int dotPos = name.ReverseFind(L'.');
- if (dotPos < 0)
- return;
- UString ext = name.Mid(dotPos + 1);
- if (ext.IsEmpty())
- return;
- for (int pos = 0; pos < ext.Length(); pos++)
- if (ext[pos] < L'0' || ext[pos] > L'9')
- return;
- name = name.Left(dotPos);
+ for (int i = Arcs.Size() - 1; i >= 0; i--)
+ {
+ RINOK(Arcs[i].Archive->Close());
+ }
+ IsOpen = false;
+ return S_OK;
}
-HRESULT OpenArchive(
+void CArchiveLink::Release()
+{
+ while (!Arcs.IsEmpty())
+ Arcs.DeleteBack();
+}
+
+HRESULT CArchiveLink::Open(
CCodecs *codecs,
const CIntVector &formatIndices,
- const UString &fileName,
- IInArchive **archive0,
- IInArchive **archive1,
- int &formatIndex0,
- int &formatIndex1,
- UString &defaultItemName0,
- UString &defaultItemName1,
- IArchiveOpenCallback *openArchiveCallback)
+ bool stdInMode,
+ IInStream *stream,
+ const UString &filePath,
+ IArchiveOpenCallback *callback)
{
- if (formatIndices.Size() >= 3)
+ Release();
+ if (formatIndices.Size() >= 32)
return E_NOTIMPL;
- int arcTypeIndex = -1;
- if (formatIndices.Size() >= 1)
- arcTypeIndex = formatIndices[formatIndices.Size() - 1];
-
- HRESULT result = OpenArchive(codecs, arcTypeIndex, fileName,
- archive0, formatIndex0, defaultItemName0, openArchiveCallback);
- RINOK(result);
+ HRESULT resSpec;
- if (formatIndices.Size() == 1)
- return S_OK;
- arcTypeIndex = -1;
- if (formatIndices.Size() >= 2)
- arcTypeIndex = formatIndices[formatIndices.Size() - 2];
-
- HRESULT resSpec = (formatIndices.Size() == 0 ? S_OK : E_NOTIMPL);
-
- CMyComPtr<IInArchiveGetStream> getStream;
- result = (*archive0)->QueryInterface(IID_IInArchiveGetStream, (void **)&getStream);
- if (result != S_OK || !getStream)
- return resSpec;
-
- CMyComPtr<ISequentialInStream> subSeqStream;
- result = getStream->GetStream(0, &subSeqStream);
- if (result != S_OK || !subSeqStream)
- return resSpec;
-
- CMyComPtr<IInStream> subStream;
- result = subSeqStream.QueryInterface(IID_IInStream, &subStream);
- if (result != S_OK || !subStream)
- return resSpec;
-
- UInt32 numItems;
- RINOK((*archive0)->GetNumberOfItems(&numItems));
- if (numItems < 1)
- return resSpec;
-
- UString subPath;
- RINOK(GetArchiveItemPath(*archive0, 0, subPath))
- if (subPath.IsEmpty())
+ for (;;)
{
- MakeDefaultName(defaultItemName0);
- subPath = defaultItemName0;
- const CArcInfoEx &format = codecs->Formats[formatIndex0];
- if (format.Name.CompareNoCase(L"7z") == 0)
+ resSpec = S_OK;
+ int formatIndex = -1;
+ if (formatIndices.Size() >= 1)
+ {
+ if (Arcs.Size() >= formatIndices.Size())
+ break;
+ formatIndex = formatIndices[formatIndices.Size() - Arcs.Size() - 1];
+ }
+ else if (Arcs.Size() >= 32)
+ break;
+
+ if (Arcs.IsEmpty())
+ {
+ CArc arc;
+ arc.Path = filePath;
+ arc.SubfileIndex = (UInt32)(Int32)-1;
+ RINOK(arc.OpenStreamOrFile(codecs, formatIndex, stdInMode, stream, callback));
+ Arcs.Add(arc);
+ continue;
+ }
+
+ const CArc &arc = Arcs.Back();
+
+ resSpec = (formatIndices.Size() == 0 ? S_OK : E_NOTIMPL);
+
+ UInt32 mainSubfile;
{
- if (subPath.Right(3).CompareNoCase(L".7z") != 0)
- subPath += L".7z";
+ NCOM::CPropVariant prop;
+ RINOK(arc.Archive->GetArchiveProperty(kpidMainSubfile, &prop));
+ if (prop.vt == VT_UI4)
+ mainSubfile = prop.ulVal;
+ else
+ break;
+ UInt32 numItems;
+ RINOK(arc.Archive->GetNumberOfItems(&numItems));
+ if (mainSubfile >= numItems)
+ break;
}
+
+
+ CMyComPtr<IInArchiveGetStream> getStream;
+ if (arc.Archive->QueryInterface(IID_IInArchiveGetStream, (void **)&getStream) != S_OK || !getStream)
+ break;
+
+ CMyComPtr<ISequentialInStream> subSeqStream;
+ if (getStream->GetStream(mainSubfile, &subSeqStream) != S_OK || !subSeqStream)
+ break;
+
+ CMyComPtr<IInStream> subStream;
+ if (subSeqStream.QueryInterface(IID_IInStream, &subStream) != S_OK || !subStream)
+ break;
+
+ CArc arc2;
+ RINOK(arc.GetItemPath(mainSubfile, arc2.Path));
+
+ CMyComPtr<IArchiveOpenSetSubArchiveName> setSubArchiveName;
+ callback->QueryInterface(IID_IArchiveOpenSetSubArchiveName, (void **)&setSubArchiveName);
+ if (setSubArchiveName)
+ setSubArchiveName->SetSubArchiveName(arc2.Path);
+
+ arc2.SubfileIndex = mainSubfile;
+ HRESULT result = arc2.OpenStream(codecs, formatIndex, subStream, NULL, callback);
+ resSpec = (formatIndices.Size() == 0 ? S_OK : S_FALSE);
+ if (result == S_FALSE)
+ break;
+ RINOK(result);
+ RINOK(arc.GetItemMTime(mainSubfile, arc2.MTime, arc2.MTimeDefined));
+ Arcs.Add(arc2);
}
- else
- subPath = ExtractFileNameFromPath(subPath);
-
- CMyComPtr<IArchiveOpenSetSubArchiveName> setSubArchiveName;
- openArchiveCallback->QueryInterface(IID_IArchiveOpenSetSubArchiveName, (void **)&setSubArchiveName);
- if (setSubArchiveName)
- setSubArchiveName->SetSubArchiveName(subPath);
-
- result = OpenArchive(codecs, arcTypeIndex, subStream, subPath,
- archive1, formatIndex1, defaultItemName1, openArchiveCallback);
- resSpec = (formatIndices.Size() == 0 ? S_OK : S_FALSE);
- if (result != S_OK)
- return resSpec;
+ IsOpen = !Arcs.IsEmpty();
return S_OK;
}
-static void SetCallback(const UString &archiveName,
- IOpenCallbackUI *openCallbackUI,
+static void SetCallback(const UString &filePath,
+ IOpenCallbackUI *callbackUI,
IArchiveOpenCallback *reOpenCallback,
- CMyComPtr<IArchiveOpenCallback> &openCallback)
+ CMyComPtr<IArchiveOpenCallback> &callback)
{
COpenCallbackImp *openCallbackSpec = new COpenCallbackImp;
- openCallback = openCallbackSpec;
- openCallbackSpec->Callback = openCallbackUI;
+ callback = openCallbackSpec;
+ openCallbackSpec->Callback = callbackUI;
openCallbackSpec->ReOpenCallback = reOpenCallback;
UString fullName;
int fileNamePartStartIndex;
- NFile::NDirectory::MyGetFullPathName(archiveName, fullName, fileNamePartStartIndex);
+ NFile::NDirectory::MyGetFullPathName(filePath, fullName, fileNamePartStartIndex);
openCallbackSpec->Init(
fullName.Left(fileNamePartStartIndex),
fullName.Mid(fileNamePartStartIndex));
}
-HRESULT MyOpenArchive(
- CCodecs *codecs,
- int arcTypeIndex,
- const UString &archiveName,
- IInArchive **archive, UString &defaultItemName, IOpenCallbackUI *openCallbackUI)
-{
- CMyComPtr<IArchiveOpenCallback> openCallback;
- SetCallback(archiveName, openCallbackUI, NULL, openCallback);
- int formatInfo;
- return OpenArchive(codecs, arcTypeIndex, archiveName, archive, formatInfo, defaultItemName, openCallback);
-}
-
-HRESULT MyOpenArchive(
- CCodecs *codecs,
+HRESULT CArchiveLink::Open2(CCodecs *codecs,
const CIntVector &formatIndices,
- const UString &archiveName,
- IInArchive **archive0,
- IInArchive **archive1,
- UString &defaultItemName0,
- UString &defaultItemName1,
- UStringVector &volumePaths,
- UInt64 &volumesSize,
- IOpenCallbackUI *openCallbackUI)
+ bool stdInMode,
+ IInStream *stream,
+ const UString &filePath,
+ IOpenCallbackUI *callbackUI)
{
- volumesSize = 0;
+ VolumesSize = 0;
COpenCallbackImp *openCallbackSpec = new COpenCallbackImp;
- CMyComPtr<IArchiveOpenCallback> openCallback = openCallbackSpec;
- openCallbackSpec->Callback = openCallbackUI;
+ CMyComPtr<IArchiveOpenCallback> callback = openCallbackSpec;
+ openCallbackSpec->Callback = callbackUI;
- UString fullName;
- int fileNamePartStartIndex;
- NFile::NDirectory::MyGetFullPathName(archiveName, fullName, fileNamePartStartIndex);
- UString prefix = fullName.Left(fileNamePartStartIndex);
- UString name = fullName.Mid(fileNamePartStartIndex);
- openCallbackSpec->Init(prefix, name);
-
- int formatIndex0, formatIndex1;
- RINOK(OpenArchive(codecs, formatIndices, archiveName,
- archive0,
- archive1,
- formatIndex0,
- formatIndex1,
- defaultItemName0,
- defaultItemName1,
- openCallback));
- volumePaths.Add(prefix + name);
- for (int i = 0; i < openCallbackSpec->FileNames.Size(); i++)
- volumePaths.Add(prefix + openCallbackSpec->FileNames[i]);
- volumesSize = openCallbackSpec->TotalSize;
- return S_OK;
-}
+ UString fullName, prefix, name;
+ if (!stream && !stdInMode)
+ {
+ int fileNamePartStartIndex;
+ if (!NFile::NDirectory::MyGetFullPathName(filePath, fullName, fileNamePartStartIndex))
+ return GetLastError();
+ prefix = fullName.Left(fileNamePartStartIndex);
+ name = fullName.Mid(fileNamePartStartIndex);
+ openCallbackSpec->Init(prefix, name);
+ }
+ else
+ {
+ openCallbackSpec->SetSubArchiveName(filePath);
+ }
-HRESULT CArchiveLink::Close()
-{
- if (Archive1 != 0)
- RINOK(Archive1->Close());
- if (Archive0 != 0)
- RINOK(Archive0->Close());
- IsOpen = false;
+ RINOK(Open(codecs, formatIndices, stdInMode, stream, filePath, callback));
+ VolumePaths.Add(prefix + name);
+ for (int i = 0; i < openCallbackSpec->FileNames.Size(); i++)
+ VolumePaths.Add(prefix + openCallbackSpec->FileNames[i]);
+ VolumesSize = openCallbackSpec->TotalSize;
return S_OK;
}
-void CArchiveLink::Release()
-{
- IsOpen = false;
- Archive1.Release();
- Archive0.Release();
-}
-
-HRESULT OpenArchive(
- CCodecs *codecs,
- const CIntVector &formatIndices,
- const UString &archiveName,
- CArchiveLink &archiveLink,
- IArchiveOpenCallback *openCallback)
-{
- HRESULT res = OpenArchive(codecs, formatIndices, archiveName,
- &archiveLink.Archive0, &archiveLink.Archive1,
- archiveLink.FormatIndex0, archiveLink.FormatIndex1,
- archiveLink.DefaultItemName0, archiveLink.DefaultItemName1,
- openCallback);
- archiveLink.IsOpen = (res == S_OK);
- return res;
-}
-
-HRESULT MyOpenArchive(CCodecs *codecs,
- const CIntVector &formatIndices,
- const UString &archiveName,
- CArchiveLink &archiveLink,
- IOpenCallbackUI *openCallbackUI)
+HRESULT CArchiveLink::ReOpen(CCodecs *codecs, const UString &filePath,
+ IArchiveOpenCallback *callback)
{
- HRESULT res = MyOpenArchive(codecs, formatIndices, archiveName,
- &archiveLink.Archive0, &archiveLink.Archive1,
- archiveLink.DefaultItemName0, archiveLink.DefaultItemName1,
- archiveLink.VolumePaths,
- archiveLink.VolumesSize,
- openCallbackUI);
- archiveLink.IsOpen = (res == S_OK);
- return res;
-}
-
-HRESULT ReOpenArchive(CCodecs *codecs, CArchiveLink &archiveLink, const UString &fileName,
- IArchiveOpenCallback *openCallback)
-{
- if (archiveLink.GetNumLevels() > 1)
+ if (Arcs.Size() > 1)
return E_NOTIMPL;
- if (archiveLink.GetNumLevels() == 0)
- return MyOpenArchive(codecs, CIntVector(), fileName, archiveLink, 0);
+ if (Arcs.Size() == 0)
+ return Open2(codecs, CIntVector(), false, NULL, filePath, 0);
CMyComPtr<IArchiveOpenCallback> openCallbackNew;
- SetCallback(fileName, NULL, openCallback, openCallbackNew);
+ SetCallback(filePath, NULL, callback, openCallbackNew);
- HRESULT res = ReOpenArchive(archiveLink.GetArchive(), fileName, openCallbackNew);
- archiveLink.IsOpen = (res == S_OK);
+ CInFileStream *fileStreamSpec = new CInFileStream;
+ CMyComPtr<IInStream> stream(fileStreamSpec);
+ if (!fileStreamSpec->Open(filePath))
+ return GetLastError();
+ HRESULT res = GetArchive()->Open(stream, &kMaxCheckStartPosition, callback);
+ IsOpen = (res == S_OK);
return res;
}
diff --git a/CPP/7zip/UI/Common/OpenArchive.h b/CPP/7zip/UI/Common/OpenArchive.h
index f1b4fda7..92103623 100755
--- a/CPP/7zip/UI/Common/OpenArchive.h
+++ b/CPP/7zip/UI/Common/OpenArchive.h
@@ -1,117 +1,86 @@
// OpenArchive.h
-#ifndef __OPENARCHIVE_H
-#define __OPENARCHIVE_H
+#ifndef __OPEN_ARCHIVE_H
+#define __OPEN_ARCHIVE_H
#include "Common/MyString.h"
+
#include "Windows/FileFind.h"
#include "../../Archive/IArchive.h"
-#include "LoadCodecs.h"
+
#include "ArchiveOpenCallback.h"
+#include "LoadCodecs.h"
-HRESULT GetArchiveItemPath(IInArchive *archive, UInt32 index, UString &result);
-HRESULT GetArchiveItemPath(IInArchive *archive, UInt32 index, const UString &defaultName, UString &result);
-HRESULT GetArchiveItemFileTime(IInArchive *archive, UInt32 index,
- const FILETIME &defaultFileTime, FILETIME &fileTime);
-HRESULT IsArchiveItemProp(IInArchive *archive, UInt32 index, PROPID propID, bool &result);
+HRESULT GetArchiveItemBoolProp(IInArchive *archive, UInt32 index, PROPID propID, bool &result);
HRESULT IsArchiveItemFolder(IInArchive *archive, UInt32 index, bool &result);
-HRESULT IsArchiveItemAnti(IInArchive *archive, UInt32 index, bool &result);
-struct ISetSubArchiveName
+struct CArc
{
- virtual void SetSubArchiveName(const wchar_t *name) = 0;
-};
-
-HRESULT OpenArchive(
+ CMyComPtr<IInArchive> Archive;
+ UString Path;
+ UString DefaultName;
+ int FormatIndex;
+ int SubfileIndex;
+ FILETIME MTime;
+ bool MTimeDefined;
+
+ CArc(): MTimeDefined(false) {}
+
+ HRESULT GetItemPath(UInt32 index, UString &result) const;
+ HRESULT GetItemMTime(UInt32 index, FILETIME &ft, bool &defined) const;
+ HRESULT IsItemAnti(UInt32 index, bool &result) const
+ { return GetArchiveItemBoolProp(Archive, index, kpidIsAnti, result); }
+
+ HRESULT OpenStream(
CCodecs *codecs,
- int arcTypeIndex,
- IInStream *inStream,
- const UString &fileName,
- IInArchive **archiveResult,
- int &formatIndex,
- UString &defaultItemName,
- IArchiveOpenCallback *openArchiveCallback);
-
-HRESULT OpenArchive(
- CCodecs *codecs,
- int arcTypeIndex,
- const UString &filePath,
- IInArchive **archive,
- int &formatIndex,
- UString &defaultItemName,
- IArchiveOpenCallback *openArchiveCallback);
+ int formatIndex,
+ IInStream *stream,
+ ISequentialInStream *seqStream,
+ IArchiveOpenCallback *callback);
-HRESULT OpenArchive(
+ HRESULT OpenStreamOrFile(
CCodecs *codecs,
- const CIntVector &formatIndices,
- const UString &filePath,
- IInArchive **archive0,
- IInArchive **archive1,
- int &formatIndex0,
- int &formatIndex1,
- UString &defaultItemName0,
- UString &defaultItemName1,
- IArchiveOpenCallback *openArchiveCallback);
-
-
-HRESULT ReOpenArchive(IInArchive *archive, const UString &fileName, IArchiveOpenCallback *openArchiveCallback);
+ int formatIndex,
+ bool stdInMode,
+ IInStream *stream,
+ IArchiveOpenCallback *callback);
+};
struct CArchiveLink
{
- CMyComPtr<IInArchive> Archive0;
- CMyComPtr<IInArchive> Archive1;
- UString DefaultItemName0;
- UString DefaultItemName1;
-
- int FormatIndex0;
- int FormatIndex1;
-
+ CObjectVector<CArc> Arcs;
UStringVector VolumePaths;
-
- bool IsOpen;
UInt64 VolumesSize;
+ bool IsOpen;
- int GetNumLevels() const
- {
- int result = 0;
- if (Archive0)
- {
- result++;
- if (Archive1)
- result++;
- }
- return result;
- }
-
- CArchiveLink(): IsOpen(false), VolumesSize(0) {};
-
- IInArchive *GetArchive() { return Archive1 != 0 ? Archive1: Archive0; }
- UString GetDefaultItemName() { return Archive1 != 0 ? DefaultItemName1: DefaultItemName0; }
- int GetArchiverIndex() const { return Archive1 != 0 ? FormatIndex1: FormatIndex0; }
+ CArchiveLink(): VolumesSize(0), IsOpen(false) {}
HRESULT Close();
void Release();
-};
+ ~CArchiveLink() { Release(); }
+
+ IInArchive *GetArchive() const { return Arcs.Back().Archive; }
-HRESULT OpenArchive(
+ HRESULT Open(
CCodecs *codecs,
const CIntVector &formatIndices,
- const UString &archiveName,
- CArchiveLink &archiveLink,
- IArchiveOpenCallback *openCallback);
+ bool stdInMode,
+ IInStream *stream,
+ const UString &filePath,
+ IArchiveOpenCallback *callback);
-HRESULT MyOpenArchive(
+ HRESULT Open2(
CCodecs *codecs,
const CIntVector &formatIndices,
- const UString &archiveName,
- CArchiveLink &archiveLink,
- IOpenCallbackUI *openCallbackUI);
+ bool stdInMode,
+ IInStream *stream,
+ const UString &filePath,
+ IOpenCallbackUI *callbackUI);
-HRESULT ReOpenArchive(
+ HRESULT ReOpen(
CCodecs *codecs,
- CArchiveLink &archiveLink,
- const UString &fileName,
- IArchiveOpenCallback *openCallback);
+ const UString &filePath,
+ IArchiveOpenCallback *callback);
+};
#endif
-
diff --git a/CPP/7zip/UI/Common/PropIDUtils.cpp b/CPP/7zip/UI/Common/PropIDUtils.cpp
index bf11ea15..d8c0e7d6 100755
--- a/CPP/7zip/UI/Common/PropIDUtils.cpp
+++ b/CPP/7zip/UI/Common/PropIDUtils.cpp
@@ -2,26 +2,18 @@
#include "StdAfx.h"
-#include "PropIDUtils.h"
-
#include "Common/IntToString.h"
-#include "Common/StringConvert.h"
#include "Windows/FileFind.h"
#include "Windows/PropVariantConversions.h"
#include "../../PropID.h"
-using namespace NWindows;
+#include "PropIDUtils.h"
-static UString ConvertUInt32ToString(UInt32 value)
-{
- wchar_t buffer[32];
- ConvertUInt64ToString(value, buffer);
- return buffer;
-}
+using namespace NWindows;
-static void ConvertUInt32ToHex(UInt32 value, wchar_t *s)
+void ConvertUInt32ToHex(UInt32 value, wchar_t *s)
{
for (int i = 0; i < 8; i++)
{
@@ -32,7 +24,9 @@ static void ConvertUInt32ToHex(UInt32 value, wchar_t *s)
s[8] = L'\0';
}
-UString ConvertPropertyToString(const PROPVARIANT &propVariant, PROPID propID, bool full)
+#define MY_ATTR_CHAR(a, n, c) ((a )& (1 << (n))) ? c : L'-';
+
+UString ConvertPropertyToString(const PROPVARIANT &prop, PROPID propID, bool full)
{
switch(propID)
{
@@ -40,50 +34,63 @@ UString ConvertPropertyToString(const PROPVARIANT &propVariant, PROPID propID, b
case kpidATime:
case kpidMTime:
{
- if (propVariant.vt != VT_FILETIME)
- return UString(); // It is error;
+ if (prop.vt != VT_FILETIME)
+ break;
FILETIME localFileTime;
- if (propVariant.filetime.dwHighDateTime == 0 &&
- propVariant.filetime.dwLowDateTime == 0)
+ if ((prop.filetime.dwHighDateTime == 0 &&
+ prop.filetime.dwLowDateTime == 0) ||
+ !::FileTimeToLocalFileTime(&prop.filetime, &localFileTime))
return UString();
- if (!::FileTimeToLocalFileTime(&propVariant.filetime, &localFileTime))
- return UString(); // It is error;
return ConvertFileTimeToString(localFileTime, true, full);
}
case kpidCRC:
{
- if(propVariant.vt != VT_UI4)
+ if (prop.vt != VT_UI4)
break;
wchar_t temp[12];
- ConvertUInt32ToHex(propVariant.ulVal, temp);
+ ConvertUInt32ToHex(prop.ulVal, temp);
return temp;
}
case kpidAttrib:
{
- if(propVariant.vt != VT_UI4)
+ if (prop.vt != VT_UI4)
break;
- UString result;
- UInt32 attributes = propVariant.ulVal;
- if (NFile::NFind::NAttributes::IsReadOnly(attributes)) result += L'R';
- if (NFile::NFind::NAttributes::IsHidden(attributes)) result += L'H';
- if (NFile::NFind::NAttributes::IsSystem(attributes)) result += L'S';
- if (NFile::NFind::NAttributes::IsDir(attributes)) result += L'D';
- if (NFile::NFind::NAttributes::IsArchived(attributes)) result += L'A';
- if (NFile::NFind::NAttributes::IsCompressed(attributes)) result += L'C';
- if (NFile::NFind::NAttributes::IsEncrypted(attributes)) result += L'E';
- return result;
+ UString res;
+ UInt32 a = prop.ulVal;
+ if (NFile::NFind::NAttributes::IsReadOnly(a)) res += L'R';
+ if (NFile::NFind::NAttributes::IsHidden(a)) res += L'H';
+ if (NFile::NFind::NAttributes::IsSystem(a)) res += L'S';
+ if (NFile::NFind::NAttributes::IsDir(a)) res += L'D';
+ if (NFile::NFind::NAttributes::IsArchived(a)) res += L'A';
+ if (NFile::NFind::NAttributes::IsCompressed(a)) res += L'C';
+ if (NFile::NFind::NAttributes::IsEncrypted(a)) res += L'E';
+ return res;
}
- case kpidDictionarySize:
+ case kpidPosixAttrib:
{
- if(propVariant.vt != VT_UI4)
+ if (prop.vt != VT_UI4)
break;
- UInt32 size = propVariant.ulVal;
- if (size % (1 << 20) == 0)
- return ConvertUInt32ToString(size >> 20) + L"MB";
- if (size % (1 << 10) == 0)
- return ConvertUInt32ToString(size >> 10) + L"KB";
- return ConvertUInt32ToString(size);
+ UString res;
+ UInt32 a = prop.ulVal;
+ wchar_t temp[16];
+ temp[0] = MY_ATTR_CHAR(a, 14, L'd');
+ for (int i = 6; i >= 0; i -= 3)
+ {
+ temp[7 - i] = MY_ATTR_CHAR(a, i + 2, L'r');
+ temp[8 - i] = MY_ATTR_CHAR(a, i + 1, L'w');
+ temp[9 - i] = MY_ATTR_CHAR(a, i + 0, L'x');
+ }
+ temp[10] = 0;
+ res = temp;
+ a &= ~0x1FF;
+ a &= ~0xC000;
+ if (a != 0)
+ {
+ ConvertUInt32ToHex(a, temp);
+ res = UString(temp) + L' ' + res;
+ }
+ return res;
}
}
- return ConvertPropVariantToString(propVariant);
+ return ConvertPropVariantToString(prop);
}
diff --git a/CPP/7zip/UI/Common/PropIDUtils.h b/CPP/7zip/UI/Common/PropIDUtils.h
index 1d820976..ca14d091 100755
--- a/CPP/7zip/UI/Common/PropIDUtils.h
+++ b/CPP/7zip/UI/Common/PropIDUtils.h
@@ -1,10 +1,12 @@
// PropIDUtils.h
-#ifndef __PROPIDUTILS_H
-#define __PROPIDUTILS_H
+#ifndef __PROPID_UTILS_H
+#define __PROPID_UTILS_H
#include "Common/MyString.h"
+#include "Common/Types.h"
+void ConvertUInt32ToHex(UInt32 value, wchar_t *s);
UString ConvertPropertyToString(const PROPVARIANT &propVariant, PROPID propID, bool full = true);
#endif
diff --git a/CPP/7zip/UI/Common/Update.cpp b/CPP/7zip/UI/Common/Update.cpp
index d8fee28b..8c8db8de 100755
--- a/CPP/7zip/UI/Common/Update.cpp
+++ b/CPP/7zip/UI/Common/Update.cpp
@@ -44,12 +44,6 @@ static const wchar_t *kTempFolderPrefix = L"7zE";
using namespace NUpdateArchive;
-static HRESULT CopyBlock(ISequentialInStream *inStream, ISequentialOutStream *outStream)
-{
- CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;
- return copyCoder->Code(inStream, outStream, NULL, NULL, NULL);
-}
-
class COutMultiVolStream:
public IOutStream,
public CMyUnknownImp
@@ -111,7 +105,7 @@ HRESULT COutMultiVolStream::Close()
STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
{
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize = 0;
while(size > 0)
{
@@ -119,15 +113,15 @@ STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *pr
{
CSubStreamInfo subStream;
- wchar_t temp[32];
- ConvertUInt64ToString(_streamIndex + 1, temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(_streamIndex + 1, temp);
UString res = temp;
while (res.Length() < 3)
res = UString(L'0') + res;
UString name = Prefix + res;
subStream.StreamSpec = new COutFileStream;
subStream.Stream = subStream.StreamSpec;
- if(!subStream.StreamSpec->Create(name, false))
+ if (!subStream.StreamSpec->Create(name, false))
return ::GetLastError();
{
// NSynchronization::CCriticalSectionLock lock(g_TempPathsCS);
@@ -173,7 +167,7 @@ STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *pr
_length = _absPos;
if (_offsetPos > subStream.RealSize)
subStream.RealSize = _offsetPos;
- if(processedSize != NULL)
+ if (processedSize != NULL)
*processedSize += realProcessed;
if (subStream.Pos == volSize)
{
@@ -189,7 +183,7 @@ STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *pr
STDMETHODIMP COutMultiVolStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
{
- if(seekOrigin >= 3)
+ if (seekOrigin >= 3)
return STG_E_INVALIDFUNCTION;
switch(seekOrigin)
{
@@ -261,6 +255,7 @@ bool CUpdateOptions::Init(const CCodecs *codecs, const CIntVector &formatIndices
else
{
MethodMode.FormatIndex = codecs->FindFormatForArchiveName(arcPath);
+ // It works incorrectly for update command if archive has some non-default extension!
if (MethodMode.FormatIndex < 0)
MethodMode.FormatIndex = codecs->FindFormatForArchiveType(kDefaultArchiveType);
}
@@ -292,7 +287,7 @@ struct CUpdateProduceCallbackImp: public IUpdateProduceCallback
const CObjectVector<CArcItem> *_arcItems;
IUpdateCallbackUI *_callback;
- CUpdateProduceCallbackImp(const CObjectVector<CArcItem> *a,
+ CUpdateProduceCallbackImp(const CObjectVector<CArcItem> *a,
IUpdateCallbackUI *callback): _arcItems(a), _callback(callback) {}
virtual HRESULT ShowDeleteFile(int arcIndex);
};
@@ -323,11 +318,11 @@ static HRESULT Compress(
IUpdateCallbackUI *callback)
{
CMyComPtr<IOutArchive> outArchive;
- if(archive != NULL)
+ if (archive != NULL)
{
CMyComPtr<IInArchive> archive2 = archive;
HRESULT result = archive2.QueryInterface(IID_IOutArchive, &outArchive);
- if(result != S_OK)
+ if (result != S_OK)
throw kUpdateIsNotSupoorted;
}
else
@@ -397,7 +392,7 @@ static HRESULT Compress(
{
UString resultPath;
int pos;
- if(!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
+ if (!NFile::NDirectory::MyGetFullPathName(archiveName, resultPath, pos))
throw 1417161;
NFile::NDirectory::CreateComplexDirectory(resultPath.Left(pos));
}
@@ -421,8 +416,8 @@ static HRESULT Compress(
{
if (i > 0)
{
- wchar_t s[32];
- ConvertUInt64ToString(i, s);
+ wchar_t s[16];
+ ConvertUInt32ToString(i, s);
archivePath.TempPostfix = s;
}
realPath = archivePath.GetTempPath();
@@ -499,7 +494,7 @@ static HRESULT Compress(
return E_FAIL;
}
}
- RINOK(CopyBlock(sfxStream, sfxOutStream));
+ RINOK(NCompress::CopyStream(sfxStream, sfxOutStream, NULL));
if (outStreamSpec)
{
RINOK(outStreamSpec->Close());
@@ -517,26 +512,22 @@ static HRESULT Compress(
}
HRESULT EnumerateInArchiveItems(const NWildcard::CCensor &censor,
- IInArchive *archive,
- const UString &defaultItemName,
- const NWindows::NFile::NFind::CFileInfoW &archiveFileInfo,
+ const CArc &arc,
CObjectVector<CArcItem> &arcItems)
{
arcItems.Clear();
UInt32 numItems;
+ IInArchive *archive = arc.Archive;
RINOK(archive->GetNumberOfItems(&numItems));
arcItems.Reserve(numItems);
for (UInt32 i = 0; i < numItems; i++)
{
CArcItem ai;
- RINOK(GetArchiveItemPath(archive, i, ai.Name));
- // check it: defaultItemName !!!
- if (ai.Name.IsEmpty())
- ai.Name = defaultItemName;
+ RINOK(arc.GetItemPath(i, ai.Name));
RINOK(IsArchiveItemFolder(archive, i, ai.IsDir));
ai.Censored = censor.CheckPath(ai.Name, !ai.IsDir);
- RINOK(GetArchiveItemFileTime(archive, i, archiveFileInfo.MTime, ai.MTime));
+ RINOK(arc.GetItemMTime(i, ai.MTime, ai.MTimeDefined));
{
CPropVariant prop;
@@ -586,7 +577,7 @@ static HRESULT UpdateWithItemLists(
CUpdateArchiveCommand &command = options.Commands[i];
if (options.StdOutMode)
{
- RINOK(callback->StartArchive(0, archive != 0));
+ RINOK(callback->StartArchive(L"stdout", archive != 0));
}
else
{
@@ -684,12 +675,10 @@ HRESULT UpdateArchive(
const UString archiveName = options.ArchivePath.GetFinalPath();
- UString defaultItemName;
+ CArchiveLink archiveLink;
NFind::CFileInfoW archiveFileInfo;
- CArchiveLink archiveLink;
- IInArchive *archive = 0;
- if (NFind::FindFile(archiveName, archiveFileInfo))
+ if (archiveFileInfo.Find(archiveName))
{
if (archiveFileInfo.IsDir())
throw "there is no such archive";
@@ -698,7 +687,7 @@ HRESULT UpdateArchive(
CIntVector formatIndices;
if (options.MethodMode.FormatIndex >= 0)
formatIndices.Add(options.MethodMode.FormatIndex);
- HRESULT result = MyOpenArchive(codecs, formatIndices, archiveName, archiveLink, openCallback);
+ HRESULT result = archiveLink.Open2(codecs, formatIndices, false, NULL, archiveName, openCallback);
if (result == E_ABORT)
return result;
RINOK(callback->OpenResult(archiveName, result));
@@ -709,8 +698,10 @@ HRESULT UpdateArchive(
errorInfo.Message = L"Updating for multivolume archives is not implemented";
return E_NOTIMPL;
}
- archive = archiveLink.GetArchive();
- defaultItemName = archiveLink.GetDefaultItemName();
+
+ CArc &arc = archiveLink.Arcs.Back();
+ arc.MTimeDefined = !archiveFileInfo.IsDevice;
+ arc.MTime = archiveFileInfo.MTime;
}
else
{
@@ -777,12 +768,15 @@ HRESULT UpdateArchive(
CTempFiles tempFiles;
bool createTempFile = false;
- if(!options.StdOutMode && options.UpdateArchiveItself)
+
+ bool thereIsInArchive = archiveLink.IsOpen;
+
+ if (!options.StdOutMode && options.UpdateArchiveItself)
{
CArchivePath &ap = options.Commands[0].ArchivePath;
ap = options.ArchivePath;
// if ((archive != 0 && !usesTempDir) || !options.WorkingDir.IsEmpty())
- if ((archive != 0 || !options.WorkingDir.IsEmpty()) && !usesTempDir && options.VolumesSizes.Size() == 0)
+ if ((thereIsInArchive || !options.WorkingDir.IsEmpty()) && !usesTempDir && options.VolumesSizes.Size() == 0)
{
createTempFile = true;
ap.Temp = true;
@@ -807,7 +801,7 @@ HRESULT UpdateArchive(
if (i > 0 || !createTempFile)
{
const UString &path = ap.GetFinalPath();
- if (NFind::DoesFileExist(path))
+ if (NFind::DoesFileOrDirExist(path))
{
errorInfo.SystemError = 0;
errorInfo.Message = L"File already exists";
@@ -818,29 +812,30 @@ HRESULT UpdateArchive(
}
CObjectVector<CArcItem> arcItems;
- if (archive != NULL)
+ if (thereIsInArchive)
{
- RINOK(EnumerateInArchiveItems(censor,
- archive, defaultItemName, archiveFileInfo, arcItems));
+ RINOK(EnumerateInArchiveItems(censor, archiveLink.Arcs.Back(), arcItems));
}
- RINOK(UpdateWithItemLists(codecs, options, archive, arcItems, dirItems,
+ RINOK(UpdateWithItemLists(codecs, options,
+ thereIsInArchive ? archiveLink.GetArchive() : 0,
+ arcItems, dirItems,
tempFiles, errorInfo, callback));
- if (archive != NULL)
+ if (thereIsInArchive)
{
RINOK(archiveLink.Close());
archiveLink.Release();
}
tempFiles.Paths.Clear();
- if(createTempFile)
+ if (createTempFile)
{
try
{
CArchivePath &ap = options.Commands[0].ArchivePath;
const UString &tempPath = ap.GetTempPath();
- if (archive != NULL)
+ if (thereIsInArchive)
if (!NDirectory::DeleteFileAlways(archiveName))
{
errorInfo.SystemError = ::GetLastError();
@@ -887,7 +882,7 @@ HRESULT UpdateArchive(
{
CArchivePath &ap = options.Commands[i].ArchivePath;
UString arcPath;
- if(!NFile::NDirectory::MyGetFullPathName(ap.GetFinalPath(), arcPath))
+ if (!NFile::NDirectory::MyGetFullPathName(ap.GetFinalPath(), arcPath))
{
errorInfo.SystemError = ::GetLastError();
return E_FAIL;
diff --git a/CPP/7zip/UI/Common/UpdateCallback.cpp b/CPP/7zip/UI/Common/UpdateCallback.cpp
index dcca2a1a..0f229058 100755
--- a/CPP/7zip/UI/Common/UpdateCallback.cpp
+++ b/CPP/7zip/UI/Common/UpdateCallback.cpp
@@ -2,17 +2,17 @@
#include "StdAfx.h"
-#include "UpdateCallback.h"
-
-#include "Common/StringConvert.h"
-#include "Common/IntToString.h"
-#include "Common/Defs.h"
#include "Common/ComTry.h"
+#include "Common/Defs.h"
+#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
#include "Windows/PropVariant.h"
#include "../../Common/FileStreams.h"
+#include "UpdateCallback.h"
+
using namespace NWindows;
CArchiveUpdateCallback::CArchiveUpdateCallback():
@@ -216,8 +216,8 @@ STDMETHODIMP CArchiveUpdateCallback::GetVolumeSize(UInt32 index, UInt64 *size)
STDMETHODIMP CArchiveUpdateCallback::GetVolumeStream(UInt32 index, ISequentialOutStream **volumeStream)
{
COM_TRY_BEGIN
- wchar_t temp[32];
- ConvertUInt64ToString(index + 1, temp);
+ wchar_t temp[16];
+ ConvertUInt32ToString(index + 1, temp);
UString res = temp;
while (res.Length() < 2)
res = UString(L'0') + res;
@@ -240,3 +240,10 @@ STDMETHODIMP CArchiveUpdateCallback::CryptoGetTextPassword2(Int32 *passwordIsDef
return Callback->CryptoGetTextPassword2(passwordIsDefined, password);
COM_TRY_END
}
+
+STDMETHODIMP CArchiveUpdateCallback::CryptoGetTextPassword(BSTR *password)
+{
+ COM_TRY_BEGIN
+ return Callback->CryptoGetTextPassword(password);
+ COM_TRY_END
+}
diff --git a/CPP/7zip/UI/Common/UpdateCallback.h b/CPP/7zip/UI/Common/UpdateCallback.h
index 2a814b37..50803f52 100755
--- a/CPP/7zip/UI/Common/UpdateCallback.h
+++ b/CPP/7zip/UI/Common/UpdateCallback.h
@@ -23,6 +23,7 @@
virtual HRESULT OpenFileError(const wchar_t *name, DWORD systemError) x; \
virtual HRESULT SetOperationResult(Int32 operationResult) x; \
virtual HRESULT CryptoGetTextPassword2(Int32 *passwordIsDefined, BSTR *password) x; \
+ virtual HRESULT CryptoGetTextPassword(BSTR *password) x; \
// virtual HRESULT ShowDeleteFile(const wchar_t *name) x; \
// virtual HRESULT CloseProgress() { return S_OK; };
@@ -34,13 +35,15 @@ struct IUpdateCallbackUI
class CArchiveUpdateCallback:
public IArchiveUpdateCallback2,
public ICryptoGetTextPassword2,
+ public ICryptoGetTextPassword,
public ICompressProgressInfo,
public CMyUnknownImp
{
public:
- MY_UNKNOWN_IMP3(
+ MY_UNKNOWN_IMP4(
IArchiveUpdateCallback2,
ICryptoGetTextPassword2,
+ ICryptoGetTextPassword,
ICompressProgressInfo)
STDMETHOD(SetRatioInfo)(const UInt64 *inSize, const UInt64 *outSize);
@@ -48,6 +51,7 @@ public:
INTERFACE_IArchiveUpdateCallback2(;)
STDMETHOD(CryptoGetTextPassword2)(Int32 *passwordIsDefined, BSTR *password);
+ STDMETHOD(CryptoGetTextPassword)(BSTR *password);
public:
CRecordVector<UInt64> VolumesSizes;
diff --git a/CPP/7zip/UI/Common/UpdatePair.cpp b/CPP/7zip/UI/Common/UpdatePair.cpp
index f6727cbf..a43a9e77 100755
--- a/CPP/7zip/UI/Common/UpdatePair.cpp
+++ b/CPP/7zip/UI/Common/UpdatePair.cpp
@@ -6,10 +6,11 @@
#include "Common/Defs.h"
#include "Common/Wildcard.h"
+
#include "Windows/Time.h"
-#include "UpdatePair.h"
#include "SortUtils.h"
+#include "UpdatePair.h"
using namespace NWindows;
using namespace NTime;
@@ -117,20 +118,16 @@ void GetUpdatePairInfoList(
ThrowError(kNotCensoredCollisionMessaged, dirNames[dirIndex2], ai.Name);
pair.DirIndex = dirIndex2;
pair.ArcIndex = arcIndex2;
- switch (MyCompareTime(
+ switch (ai.MTimeDefined ? MyCompareTime(
ai.TimeType != - 1 ? (NFileTimeType::EEnum)ai.TimeType : fileTimeType,
- di.MTime, ai.MTime))
+ di.MTime, ai.MTime): 0)
{
case -1: pair.State = NUpdateArchive::NPairState::kNewInArchive; break;
case 1: pair.State = NUpdateArchive::NPairState::kOldInArchive; break;
default:
- if (ai.SizeDefined)
- if (di.Size != ai.Size)
- pair.State = NUpdateArchive::NPairState::kUnknowNewerFiles;
- else
- pair.State = NUpdateArchive::NPairState::kSameFiles;
- else
- pair.State = NUpdateArchive::NPairState::kUnknowNewerFiles;
+ pair.State = (ai.SizeDefined && di.Size == ai.Size) ?
+ NUpdateArchive::NPairState::kSameFiles :
+ NUpdateArchive::NPairState::kUnknowNewerFiles;
}
dirIndex++;
arcIndex++;
diff --git a/CPP/7zip/UI/Common/ZipRegistry.cpp b/CPP/7zip/UI/Common/ZipRegistry.cpp
index 4bba19f8..16df878f 100755
--- a/CPP/7zip/UI/Common/ZipRegistry.cpp
+++ b/CPP/7zip/UI/Common/ZipRegistry.cpp
@@ -46,7 +46,7 @@ void SaveExtractionInfo(const NExtract::CInfo &info)
for(int i = 0; i < info.Paths.Size(); i++)
{
wchar_t numberString[16];
- ConvertUInt64ToString(i, numberString);
+ ConvertUInt32ToString(i, numberString);
pathHistoryKey.SetValue(numberString, info.Paths[i]);
}
}
@@ -75,7 +75,7 @@ void ReadExtractionInfo(NExtract::CInfo &info)
for (;;)
{
wchar_t numberString[16];
- ConvertUInt64ToString(info.Paths.Size(), numberString);
+ ConvertUInt32ToString(info.Paths.Size(), numberString);
UString path;
if (pathHistoryKey.QueryValue(numberString, path) != ERROR_SUCCESS)
break;
@@ -180,7 +180,7 @@ void SaveCompressionInfo(const NCompression::CInfo &info)
for(int i = 0; i < info.HistoryArchives.Size(); i++)
{
wchar_t numberString[16];
- ConvertUInt64ToString(i, numberString);
+ ConvertUInt32ToString(i, numberString);
historyArchivesKey.SetValue(numberString, info.HistoryArchives[i]);
}
}
@@ -246,7 +246,7 @@ void ReadCompressionInfo(NCompression::CInfo &info)
for (;;)
{
wchar_t numberString[16];
- ConvertUInt64ToString(info.HistoryArchives.Size(), numberString);
+ ConvertUInt32ToString(info.HistoryArchives.Size(), numberString);
UString path;
if (historyArchivesKey.QueryValue(numberString, path) != ERROR_SUCCESS)
break;
diff --git a/CPP/7zip/UI/Console/Console.dsp b/CPP/7zip/UI/Console/Console.dsp
index bb2f0e1d..c6aeefed 100755
--- a/CPP/7zip/UI/Console/Console.dsp
+++ b/CPP/7zip/UI/Console/Console.dsp
@@ -44,7 +44,7 @@ RSC=rc.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "../../../" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "../../../" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE RSC /l 0x419 /d "NDEBUG"
# ADD RSC /l 0x419 /d "NDEBUG"
BSC32=bscmake.exe
@@ -69,7 +69,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
-# ADD CPP /nologo /Gz /MTd /W3 /Gm /GX /ZI /Od /I "../../../" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MTd /W3 /Gm /GX /ZI /Od /I "../../../" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE RSC /l 0x419 /d "_DEBUG"
# ADD RSC /l 0x419 /d "_DEBUG"
BSC32=bscmake.exe
@@ -94,7 +94,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /Gz /MD /W3 /GX /O1 /I "../../../" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /Yu"StdAfx.h" /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "../../../" /D "NDEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "../../../" /D "NDEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE RSC /l 0x419 /d "NDEBUG"
# ADD RSC /l 0x419 /d "NDEBUG"
BSC32=bscmake.exe
@@ -120,7 +120,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /Gz /W3 /Gm /GX /ZI /Od /I "../../../" /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /Yu"StdAfx.h" /FD /GZ /c
-# ADD CPP /nologo /Gz /W3 /Gm /GX /ZI /Od /I "../../../" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /W3 /Gm /GX /ZI /Od /I "../../../" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_CONSOLE" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BREAK_HANDLER" /D "BENCH_MT" /D "_7ZIP_LARGE_PAGES" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE RSC /l 0x419 /d "_DEBUG"
# ADD RSC /l 0x419 /d "_DEBUG"
BSC32=bscmake.exe
@@ -734,5 +734,17 @@ SOURCE=..\..\..\..\C\Threads.c
SOURCE=..\..\..\..\C\Threads.h
# End Source File
# End Group
+# Begin Group "ArchiveCommon"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.h
+# End Source File
+# End Group
# End Target
# End Project
diff --git a/CPP/7zip/UI/Console/List.cpp b/CPP/7zip/UI/Console/List.cpp
index 82a08f2f..4352bc71 100755
--- a/CPP/7zip/UI/Console/List.cpp
+++ b/CPP/7zip/UI/Console/List.cpp
@@ -2,25 +2,23 @@
#include "StdAfx.h"
-#include "List.h"
-#include "ConsoleClose.h"
-
-#include "Common/StringConvert.h"
-#include "Common/StdOutStream.h"
#include "Common/IntToString.h"
#include "Common/MyCom.h"
+#include "Common/StdOutStream.h"
+#include "Common/StringConvert.h"
+#include "Windows/Error.h"
+#include "Windows/FileDir.h"
#include "Windows/PropVariant.h"
-#include "Windows/Defs.h"
#include "Windows/PropVariantConversions.h"
-#include "Windows/FileDir.h"
-#include "Windows/Error.h"
#include "../../Archive/IArchive.h"
-#include "../Common/PropIDUtils.h"
#include "../Common/OpenArchive.h"
+#include "../Common/PropIDUtils.h"
+#include "ConsoleClose.h"
+#include "List.h"
#include "OpenCallbackConsole.h"
using namespace NWindows;
@@ -78,8 +76,17 @@ static CPropIdToName kPropIdToName[] =
{ kpidChecksum, L"Checksum" },
{ kpidCharacts, L"Characteristics" },
{ kpidVa, L"Virtual Address" },
+ { kpidId, L"ID" },
+ { kpidShortName, L"Short Name" },
+ { kpidCreatorApp, L"Creator Application"},
+ { kpidSectorSize, L"Sector Size" },
+ { kpidPosixAttrib, L"Mode" },
+ { kpidLink, L"Link" },
+
+ { kpidTotalSize, L"Total Size" },
{ kpidFreeSpace, L"Free Space" },
- { kpidClusterSize, L"Cluster Size" }
+ { kpidClusterSize, L"Cluster Size" },
+ { kpidVolumeName, L"Label" }
};
static const char kEmptyAttribChar = '.';
@@ -125,7 +132,7 @@ struct CFieldInfoInit
int Width;
};
-CFieldInfoInit kStandardFieldTable[] =
+static CFieldInfoInit kStandardFieldTable[] =
{
{ kpidMTime, L" Date Time", kLeft, kLeft, 0, 19 },
{ kpidAttrib, L"Attr", kRight, kCenter, 1, 5 },
@@ -134,13 +141,13 @@ CFieldInfoInit kStandardFieldTable[] =
{ kpidPath, L"Name", kLeft, kLeft, 2, 24 }
};
-void PrintSpaces(int numSpaces)
+static void PrintSpaces(int numSpaces)
{
for (int i = 0; i < numSpaces; i++)
g_StdOut << ' ';
}
-void PrintString(EAdjustment adjustment, int width, const UString &textString)
+static void PrintString(EAdjustment adjustment, int width, const UString &textString)
{
const int numSpaces = width - textString.Length();
int numLeftSpaces = 0;
@@ -170,10 +177,7 @@ public:
HRESULT Init(IInArchive *archive);
void PrintTitle();
void PrintTitleLines();
- HRESULT PrintItemInfo(IInArchive *archive,
- const UString &defaultItemName,
- UInt32 index,
- bool techMode);
+ HRESULT PrintItemInfo(const CArc &arc, UInt32 index, bool techMode);
HRESULT PrintSummaryInfo(UInt64 numFiles, UInt64 numDirs,
const UInt64 *size, const UInt64 *compressedSize);
};
@@ -205,8 +209,8 @@ static UString GetPropName(PROPID propID, BSTR name)
}
if (name)
return name;
- wchar_t s[32];
- ConvertUInt64ToString(propID, s);
+ wchar_t s[16];
+ ConvertUInt32ToString(propID, s);
return s;
}
@@ -252,13 +256,13 @@ void CFieldPrinter::PrintTitleLines()
}
-BOOL IsFileTimeZero(CONST FILETIME *lpFileTime)
+static BOOL IsFileTimeZero(CONST FILETIME *lpFileTime)
{
return (lpFileTime->dwLowDateTime == 0) && (lpFileTime->dwHighDateTime == 0);
}
static const char *kEmptyTimeString = " ";
-void PrintTime(const NCOM::CPropVariant &prop)
+static void PrintTime(const NCOM::CPropVariant &prop)
{
if (prop.vt != VT_FILETIME)
throw "incorrect item";
@@ -277,10 +281,7 @@ void PrintTime(const NCOM::CPropVariant &prop)
}
}
-HRESULT CFieldPrinter::PrintItemInfo(IInArchive *archive,
- const UString &defaultItemName,
- UInt32 index,
- bool techMode)
+HRESULT CFieldPrinter::PrintItemInfo(const CArc &arc, UInt32 index, bool techMode)
{
/*
if (techMode)
@@ -300,45 +301,35 @@ HRESULT CFieldPrinter::PrintItemInfo(IInArchive *archive,
if (fieldInfo.PropID == kpidPath)
{
UString s;
- RINOK(GetArchiveItemPath(archive, index, defaultItemName, s));
+ RINOK(arc.GetItemPath(index, s));
prop = s;
}
else
{
- RINOK(archive->GetProperty(index, fieldInfo.PropID, &prop));
+ RINOK(arc.Archive->GetProperty(index, fieldInfo.PropID, &prop));
}
if (techMode)
{
g_StdOut << fieldInfo.Name << " = ";
}
int width = (fieldInfo.PropID == kpidPath) ? 0: fieldInfo.Width;
- if (prop.vt == VT_EMPTY)
+ if (fieldInfo.PropID == kpidAttrib && (prop.vt == VT_EMPTY || prop.vt == VT_UI4))
{
- switch(fieldInfo.PropID)
- {
- case kpidPath: prop = defaultItemName; break;
- default:
- if (techMode)
- g_StdOut << endl;
- else
- PrintSpaces(width);
- continue;
- }
+ UInt32 attrib = (prop.vt == VT_EMPTY) ? 0 : prop.ulVal;
+ bool isFolder;
+ RINOK(IsArchiveItemFolder(arc.Archive, index, isFolder));
+ char s[8];
+ GetAttribString(attrib, isFolder, s);
+ g_StdOut << s;
}
- if (fieldInfo.PropID == kpidMTime)
+ else if (prop.vt == VT_EMPTY)
{
- PrintTime(prop);
+ if (!techMode)
+ PrintSpaces(width);
}
- else if (fieldInfo.PropID == kpidAttrib)
+ else if (fieldInfo.PropID == kpidMTime)
{
- if (prop.vt != VT_UI4)
- throw "incorrect item";
- UInt32 attributes = prop.ulVal;
- bool isFolder;
- RINOK(IsArchiveItemFolder(archive, index, isFolder));
- char s[8];
- GetAttribString(attributes, isFolder, s);
- g_StdOut << s;
+ PrintTime(prop);
}
else if (prop.vt == VT_BSTR)
{
@@ -364,7 +355,7 @@ HRESULT CFieldPrinter::PrintItemInfo(IInArchive *archive,
return S_OK;
}
-void PrintNumberString(EAdjustment adjustment, int width, const UInt64 *value)
+static void PrintNumberString(EAdjustment adjustment, int width, const UInt64 *value)
{
wchar_t textString[32] = { 0 };
if (value != NULL)
@@ -416,8 +407,14 @@ bool GetUInt64Value(IInArchive *archive, UInt32 index, PROPID propID, UInt64 &va
return true;
}
+static void PrintPropPair(const wchar_t *name, const wchar_t *value)
+{
+ g_StdOut << name << " = " << value << endl;
+}
+
HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
- UStringVector &archivePaths, UStringVector &archivePathsFull,
+ bool stdInMode,
+ UStringVector &arcPaths, UStringVector &arcPathsFull,
const NWildcard::CCensorNode &wildcardCensor,
bool enableHeaders, bool techMode,
#ifndef _NO_CRYPTO
@@ -432,15 +429,19 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
UInt64 numFiles2 = 0, numDirs2 = 0, totalPackSize2 = 0, totalUnPackSize2 = 0;
UInt64 *totalPackSizePointer2 = 0, *totalUnPackSizePointer2 = 0;
- for (int i = 0; i < archivePaths.Size(); i++)
+ int numArcs = /* stdInMode ? 1 : */ arcPaths.Size();
+ for (int i = 0; i < numArcs; i++)
{
- const UString &archiveName = archivePaths[i];
- NFile::NFind::CFileInfoW fi;
- if (!NFile::NFind::FindFile(archiveName, fi) || fi.IsDir())
+ const UString &archiveName = arcPaths[i];
+ if (!stdInMode)
{
- g_StdOut << endl << "Error: " << archiveName << " is not file" << endl;
- numErrors++;
- continue;
+ NFile::NFind::CFileInfoW fi;
+ if (!fi.Find(archiveName) || fi.IsDir())
+ {
+ g_StdOut << endl << "Error: " << archiveName << " is not file" << endl;
+ numErrors++;
+ continue;
+ }
}
CArchiveLink archiveLink;
@@ -455,14 +456,21 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
#endif
- HRESULT result = MyOpenArchive(codecs, formatIndices, archiveName, archiveLink, &openCallback);
+ HRESULT result = archiveLink.Open2(codecs, formatIndices, stdInMode, NULL, archiveName, &openCallback);
if (result != S_OK)
{
if (result == E_ABORT)
return result;
g_StdOut << endl << "Error: " << archiveName << ": ";
if (result == S_FALSE)
- g_StdOut << "is not supported archive";
+ {
+ #ifndef _NO_CRYPTO
+ if (openCallback.Open_WasPasswordAsked())
+ g_StdOut << "Can not open encrypted archive. Wrong password?";
+ else
+ #endif
+ g_StdOut << "Can not open file as archive";
+ }
else if (result == E_OUTOFMEMORY)
g_StdOut << "Can't allocate required memory";
else
@@ -472,45 +480,52 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
continue;
}
+ if (!stdInMode)
for (int v = 0; v < archiveLink.VolumePaths.Size(); v++)
{
- int index = archivePathsFull.FindInSorted(archiveLink.VolumePaths[v]);
+ int index = arcPathsFull.FindInSorted(archiveLink.VolumePaths[v]);
if (index >= 0 && index > i)
{
- archivePaths.Delete(index);
- archivePathsFull.Delete(index);
+ arcPaths.Delete(index);
+ arcPathsFull.Delete(index);
+ numArcs = arcPaths.Size();
}
}
- IInArchive *archive = archiveLink.GetArchive();
- const UString defaultItemName = archiveLink.GetDefaultItemName();
-
if (enableHeaders)
{
g_StdOut << endl << kListing << archiveName << endl << endl;
- UInt32 numProps;
- if (archive->GetNumberOfArchiveProperties(&numProps) == S_OK)
+ for (int i = 0; i < archiveLink.Arcs.Size(); i++)
{
- for (UInt32 i = 0; i < numProps; i++)
+ const CArc &arc = archiveLink.Arcs[i];
+
+ g_StdOut << "----\n";
+ PrintPropPair(L"Path", arc.Path);
+ PrintPropPair(L"Type", codecs->Formats[arc.FormatIndex].Name);
+ UInt32 numProps;
+ IInArchive *archive = arc.Archive;
+ if (archive->GetNumberOfArchiveProperties(&numProps) == S_OK)
{
- CMyComBSTR name;
- PROPID propID;
- VARTYPE vt;
- if (archive->GetArchivePropertyInfo(i, &name, &propID, &vt) != S_OK)
- continue;
- NCOM::CPropVariant prop;
- if (archive->GetArchiveProperty(propID, &prop) != S_OK)
- continue;
- UString s = ConvertPropertyToString(prop, propID);
- if (!s.IsEmpty())
- g_StdOut << GetPropName(propID, name) << " = " << s << endl;
+ for (UInt32 j = 0; j < numProps; j++)
+ {
+ CMyComBSTR name;
+ PROPID propID;
+ VARTYPE vt;
+ if (archive->GetArchivePropertyInfo(j, &name, &propID, &vt) != S_OK)
+ continue;
+ NCOM::CPropVariant prop;
+ if (archive->GetArchiveProperty(propID, &prop) != S_OK)
+ continue;
+ UString s = ConvertPropertyToString(prop, propID);
+ if (!s.IsEmpty())
+ PrintPropPair(GetPropName(propID, name), s);
+ }
}
}
+ g_StdOut << endl;
if (techMode)
g_StdOut << "----------\n";
- if (numProps > 0)
- g_StdOut << endl;
}
if (enableHeaders && !techMode)
@@ -521,6 +536,8 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
g_StdOut << endl;
}
+ const CArc &arc = archiveLink.Arcs.Back();
+ IInArchive *archive = arc.Archive;
if (techMode)
{
RINOK(fieldPrinter.Init(archive));
@@ -529,20 +546,23 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
UInt64 *totalPackSizePointer = 0, *totalUnPackSizePointer = 0;
UInt32 numItems;
RINOK(archive->GetNumberOfItems(&numItems));
- for(UInt32 i = 0; i < numItems; i++)
+ for (UInt32 i = 0; i < numItems; i++)
{
if (NConsoleClose::TestBreakSignal())
return E_ABORT;
UString filePath;
- RINOK(GetArchiveItemPath(archive, i, defaultItemName, filePath));
+ HRESULT res = arc.GetItemPath(i, filePath);
+ if (stdInMode && res == E_INVALIDARG)
+ break;
+ RINOK(res);
bool isFolder;
RINOK(IsArchiveItemFolder(archive, i, isFolder));
if (!wildcardCensor.CheckPath(filePath, !isFolder))
continue;
- fieldPrinter.PrintItemInfo(archive, defaultItemName, i, techMode);
+ fieldPrinter.PrintItemInfo(arc, i, techMode);
UInt64 packSize, unpackSize;
if (!GetUInt64Value(archive, i, kpidSize, unpackSize))
@@ -583,14 +603,14 @@ HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
numFiles2 += numFiles;
numDirs2 += numDirs;
}
- if (enableHeaders && !techMode && archivePaths.Size() > 1)
+ if (enableHeaders && !techMode && numArcs > 1)
{
g_StdOut << endl;
fieldPrinter.PrintTitleLines();
g_StdOut << endl;
fieldPrinter.PrintSummaryInfo(numFiles2, numDirs2, totalUnPackSizePointer2, totalPackSizePointer2);
g_StdOut << endl;
- g_StdOut << "Archives: " << archivePaths.Size() << endl;
+ g_StdOut << "Archives: " << numArcs << endl;
}
return S_OK;
}
diff --git a/CPP/7zip/UI/Console/List.h b/CPP/7zip/UI/Console/List.h
index bb4287e6..97d9fb15 100755
--- a/CPP/7zip/UI/Console/List.h
+++ b/CPP/7zip/UI/Console/List.h
@@ -7,6 +7,7 @@
#include "../Common/LoadCodecs.h"
HRESULT ListArchives(CCodecs *codecs, const CIntVector &formatIndices,
+ bool stdInMode,
UStringVector &archivePaths, UStringVector &archivePathsFull,
const NWildcard::CCensorNode &wildcardCensor,
bool enableHeaders, bool techMode,
diff --git a/CPP/7zip/UI/Console/Main.cpp b/CPP/7zip/UI/Console/Main.cpp
index 87d48e95..368a9667 100755
--- a/CPP/7zip/UI/Console/Main.cpp
+++ b/CPP/7zip/UI/Console/Main.cpp
@@ -5,45 +5,44 @@
#include "Common/MyInitGuid.h"
#include "Common/CommandLineParser.h"
-#include "Common/MyException.h"
#include "Common/IntToString.h"
+#include "Common/MyException.h"
#include "Common/StdOutStream.h"
#include "Common/StringConvert.h"
#include "Common/StringToInt.h"
-#include "Windows/FileDir.h"
-#include "Windows/FileName.h"
#include "Windows/Defs.h"
#include "Windows/Error.h"
+#include "Windows/FileDir.h"
+#include "Windows/FileName.h"
#ifdef _WIN32
#include "Windows/MemoryLock.h"
#endif
-#include "../../IPassword.h"
#include "../../ICoder.h"
-#include "../Common/UpdateAction.h"
-#include "../Common/Update.h"
-#include "../Common/Extract.h"
+#include "../../IPassword.h"
+
#include "../Common/ArchiveCommandLine.h"
#include "../Common/ExitCode.h"
+#include "../Common/Extract.h"
#ifdef EXTERNAL_CODECS
#include "../Common/LoadCodecs.h"
#endif
+#include "../Common/PropIDUtils.h"
+#include "../Common/Update.h"
+#include "../Common/UpdateAction.h"
#include "../../Compress/LZMA_Alone/LzmaBenchCon.h"
+#include "ExtractCallbackConsole.h"
#include "List.h"
#include "OpenCallbackConsole.h"
-#include "ExtractCallbackConsole.h"
#include "UpdateCallbackConsole.h"
#include "../../MyVersion.h"
#if defined( _WIN32) && defined( _7ZIP_LARGE_PAGES)
-extern "C"
-{
#include "../../../../C/Alloc.h"
-}
#endif
using namespace NWindows;
@@ -108,8 +107,8 @@ static const char *kHelpString =
" -ssc[-]: set sensitive case mode\n"
" -ssw: compress shared files\n"
" -t{Type}: Set type of archive\n"
- " -v{Size}[b|k|m|g]: Create volumes\n"
" -u[-][p#][q#][r#][x#][y#][z#][!newArchiveName]: Update options\n"
+ " -v{Size}[b|k|m|g]: Create volumes\n"
" -w[{path}]: assign Work directory. Empty path means a temporary directory\n"
" -x[r[-|0]]]{@listfile|!wildcard}: eXclude filenames\n"
" -y: assume Yes on all queries\n";
@@ -197,7 +196,7 @@ int Main2(
GetArguments(numArguments, arguments, commandStrings);
#endif
- if(commandStrings.Size() == 1)
+ if (commandStrings.Size() == 1)
{
ShowCopyrightAndHelp(g_StdOut, true);
return 0;
@@ -210,7 +209,7 @@ int Main2(
parser.Parse1(commandStrings, options);
- if(options.HelpMode)
+ if (options.HelpMode)
{
ShowCopyrightAndHelp(g_StdOut, true);
return 0;
@@ -266,8 +265,8 @@ int Main2(
#ifdef EXTERNAL_CODECS
if (arc.LibIndex >= 0)
{
- char s[32];
- ConvertUInt64ToString(arc.LibIndex, s);
+ char s[16];
+ ConvertUInt32ToString(arc.LibIndex, s);
PrintString(stdStream, s, 2);
}
else
@@ -321,8 +320,8 @@ int Main2(
int libIndex = codecs->GetCodecLibIndex(j);
if (libIndex >= 0)
{
- char s[32];
- ConvertUInt64ToString(libIndex, s);
+ char s[16];
+ ConvertUInt32ToString(libIndex, s);
PrintString(stdStream, s, 2);
}
else
@@ -383,7 +382,7 @@ int Main2(
}
else if (isExtractGroupCommand || options.Command.CommandType == NCommandType::kList)
{
- if(isExtractGroupCommand)
+ if (isExtractGroupCommand)
{
CExtractCallbackConsole *ecs = new CExtractCallbackConsole;
CMyComPtr<IFolderArchiveExtractCallback> extractCallback = ecs;
@@ -406,12 +405,14 @@ int Main2(
#endif
CExtractOptions eo;
+ eo.StdInMode = options.StdInMode;
eo.StdOutMode = options.StdOutMode;
eo.PathMode = options.Command.GetPathMode();
eo.TestMode = options.Command.IsTestMode();
eo.OverwriteMode = options.OverwriteMode;
eo.OutputDir = options.OutputDir;
eo.YesToAll = options.YesToAll;
+ eo.CalcCrc = options.CalcCrc;
#ifdef COMPRESS_MT
eo.Properties = options.ExtractProperties;
#endif
@@ -457,6 +458,12 @@ int Main2(
stdStream
<< "Size: " << stat.UnpackSize << endl
<< "Compressed: " << stat.PackSize << endl;
+ if (options.CalcCrc)
+ {
+ wchar_t s[16];
+ ConvertUInt32ToHex(stat.CrcSum, s);
+ stdStream << "CRC: " << s << endl;
+ }
}
else
{
@@ -464,6 +471,7 @@ int Main2(
HRESULT result = ListArchives(
codecs,
formatIndices,
+ options.StdInMode,
options.ArchivePathsSorted,
options.ArchivePathsFullSorted,
options.WildcardCensor.Pairs.Front().Head,
@@ -483,10 +491,8 @@ int Main2(
throw CSystemException(result);
}
}
- else if(options.Command.IsFromUpdateGroup())
+ else if (options.Command.IsFromUpdateGroup())
{
- UString workingDir;
-
CUpdateOptions &uo = options.UpdateOptions;
if (uo.SfxMode && uo.SfxModule.IsEmpty())
uo.SfxModule = kDefaultSfxModule;
diff --git a/CPP/7zip/UI/Console/UpdateCallbackConsole.cpp b/CPP/7zip/UI/Console/UpdateCallbackConsole.cpp
index bf22d34b..ccb6c866 100755
--- a/CPP/7zip/UI/Console/UpdateCallbackConsole.cpp
+++ b/CPP/7zip/UI/Console/UpdateCallbackConsole.cpp
@@ -196,10 +196,12 @@ HRESULT CUpdateCallbackConsole::SetOperationResult(Int32 )
HRESULT CUpdateCallbackConsole::CryptoGetTextPassword2(Int32 *passwordIsDefined, BSTR *password)
{
+ *password = NULL;
+
#ifdef _NO_CRYPTO
*passwordIsDefined = false;
- return StringToBstr(L"", password);
+ return S_OK;
#else
@@ -215,7 +217,28 @@ HRESULT CUpdateCallbackConsole::CryptoGetTextPassword2(Int32 *passwordIsDefined,
return StringToBstr(Password, password);
#endif
+}
+
+HRESULT CUpdateCallbackConsole::CryptoGetTextPassword(BSTR *password)
+{
+ *password = NULL;
+
+ #ifdef _NO_CRYPTO
+
+ return E_NOTIMPL;
+
+ #else
+ if (!PasswordIsDefined)
+ {
+ {
+ Password = GetPassword(OutStream);
+ PasswordIsDefined = true;
+ }
+ }
+ return StringToBstr(Password, password);
+
+ #endif
}
/*
diff --git a/CPP/7zip/UI/Console/UpdateCallbackConsole.h b/CPP/7zip/UI/Console/UpdateCallbackConsole.h
index da8d8cc2..5ffe3eb7 100755
--- a/CPP/7zip/UI/Console/UpdateCallbackConsole.h
+++ b/CPP/7zip/UI/Console/UpdateCallbackConsole.h
@@ -1,13 +1,14 @@
// UpdateCallbackConsole.h
-#ifndef __UPDATECALLBACKCONSOLE_H
-#define __UPDATECALLBACKCONSOLE_H
+#ifndef __UPDATE_CALLBACK_CONSOLE_H
+#define __UPDATE_CALLBACK_CONSOLE_H
-#include "Common/MyString.h"
#include "Common/StdOutStream.h"
-#include "PercentPrinter.h"
+
#include "../Common/Update.h"
+#include "PercentPrinter.h"
+
class CUpdateCallbackConsole: public IUpdateCallbackUI2
{
CPercentPrinter m_PercentPrinter;
diff --git a/CPP/7zip/UI/Console/UserInputUtils.cpp b/CPP/7zip/UI/Console/UserInputUtils.cpp
index b85cd594..798486e7 100755
--- a/CPP/7zip/UI/Console/UserInputUtils.cpp
+++ b/CPP/7zip/UI/Console/UserInputUtils.cpp
@@ -51,6 +51,5 @@ UString GetPassword(CStdOutStream *outStream)
{
(*outStream) << "\nEnter password:";
outStream->Flush();
- AString oemPassword = g_StdIn.ScanStringUntilNewLine();
- return MultiByteToUnicodeString(oemPassword, CP_OEMCP);
+ return g_StdIn.ScanUStringUntilNewLine();
}
diff --git a/CPP/7zip/UI/Console/makefile b/CPP/7zip/UI/Console/makefile
index 01682e9a..a0d56615 100755
--- a/CPP/7zip/UI/Console/makefile
+++ b/CPP/7zip/UI/Console/makefile
@@ -8,6 +8,7 @@ CFLAGS = $(CFLAGS) -I ../../../ \
-DBREAK_HANDLER \
-DBENCH_MT \
-D_7ZIP_LARGE_PAGES \
+ -DSUPPORT_DEVICE_FILE \
CONSOLE_OBJS = \
$O\ConsoleClose.obj \
@@ -76,6 +77,9 @@ UI_COMMON_OBJS = \
$O\UpdateProduce.obj \
$O\WorkDir.obj \
+AR_COMMON_OBJS = \
+ $O\OutStreamWithCRC.obj \
+
LZMA_BENCH_OBJS = \
$O\LzmaBench.obj \
$O\LzmaBenchCon.obj \
@@ -93,6 +97,7 @@ OBJS = \
$(WIN_OBJS) \
$(7ZIP_COMMON_OBJS) \
$(UI_COMMON_OBJS) \
+ $(AR_COMMON_OBJS) \
$O\CopyCoder.obj \
$(LZMA_BENCH_OBJS) \
$(C_OBJS) \
@@ -111,6 +116,8 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(UI_COMMON_OBJS): ../Common/$(*B).cpp
$(COMPL)
+$(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
+ $(COMPL)
$O\CopyCoder.obj: ../../Compress/$(*B).cpp
$(COMPL)
$(LZMA_BENCH_OBJS): ../../Compress/LZMA_Alone/$(*B).cpp
diff --git a/CPP/7zip/UI/Explorer/ContextMenu.cpp b/CPP/7zip/UI/Explorer/ContextMenu.cpp
index 3ba8f3eb..efe8ad44 100755
--- a/CPP/7zip/UI/Explorer/ContextMenu.cpp
+++ b/CPP/7zip/UI/Explorer/ContextMenu.cpp
@@ -5,40 +5,30 @@
#include "ContextMenu.h"
#include "Common/StringConvert.h"
-#include "Common/MyCom.h"
-#include "Windows/Shell.h"
-#include "Windows/Memory.h"
#include "Windows/COM.h"
-#include "Windows/FileFind.h"
#include "Windows/FileDir.h"
-#include "Windows/FileName.h"
-#include "Windows/Thread.h"
-#include "Windows/Window.h"
-
+#include "Windows/FileFind.h"
+#include "Windows/Memory.h"
#include "Windows/Menu.h"
-#include "Windows/ResourceString.h"
+#include "Windows/Shell.h"
+
+#include "../Common/ArchiveName.h"
+#include "../Common/CompressCall.h"
+#include "../Common/ExtractingFilePath.h"
+#include "../Common/ZipRegistry.h"
#include "../FileManager/FormatUtils.h"
#include "../FileManager/ProgramLocation.h"
-#include "../Common/ZipRegistry.h"
-#include "../Common/ArchiveName.h"
-
#ifdef LANG
#include "../FileManager/LangUtils.h"
#endif
-#include "resource.h"
#include "ContextMenuFlags.h"
-
-// #include "ExtractEngine.h"
-// #include "TestEngine.h"
-// #include "CompressEngine.h"
#include "MyMessages.h"
-#include "../GUI/ExtractRes.h"
-#include "../Common/CompressCall.h"
+#include "resource.h"
using namespace NWindows;
@@ -297,7 +287,7 @@ static UString GetSubFolderNameForExtract(const UString &archiveName)
res = res.Left(dotPos);
res.TrimRight();
}
- return res;
+ return GetCorrectFullFsPath(res);
}
static UString GetReducedString(const UString &s)
@@ -316,27 +306,34 @@ static UString GetQuotedString(const UString &s)
static UString GetQuotedReducedString(const UString &s)
{
- return GetQuotedString(GetReducedString(s));
+ UString s2 = GetReducedString(s);
+ s2.Replace(L"&", L"&&");
+ return GetQuotedString(s2);
}
-static const wchar_t *kExtractExludeExtensions[] =
-{
- L"txt", L"htm", L"html", L"xml", L"xsd", L"xsl", L"xslt", L"asp", L"aspx", L"css", L"shtml",
- L"bmp", L"gif", L"jpeg", L"jpg", L"png", L"tiff", L"ico",
- L"3gp", L"avi", L"mov", L"mpeg", L"mpg", L"mpe", L"wmv",
- L"aac", L"ape", L"fla", L"flac", L"la", L"mp3", L"m4a", L"mp4", L"ofr", L"ogg",
- L"pac", L"ra", L"rm", L"rka", L"shn", L"swa", L"tta", L"wv", L"wma", L"wav",
- L"ps", L"eps",
- L"inl", L"inc", L"idl", L"h", L"hpp", L"hxx", L"c", L"cpp", L"cxx", L"rc", L"java",
- L"cs", L"pas", L"bas", L"vb", L"cls", L"ctl", L"frm", L"dlg", L"def",
- L"f77", L"f", L"f90", L"f95",
- L"asm", L"sql", L"manifest", L"dep",
- L"mak", L"clw", L"csproj", L"vcproj", L"sln", L"dsp", L"dsw",
- L"bat", L"cmd",
- L"awk", L"sed", L"hta", L"js", L"php", L"php3", L"php4", L"php5",
- L"phptml", L"pl", L"pm", L"py", L"pyo", L"rb", L"sh", L"tcl", L"vbs",
- L"tex", L"ans", L"asc", L"srt", L"reg", L"ini", L"rtf", L"pdf"
-};
+static const char *kExtractExludeExtensions =
+ " 3gp"
+ " aac ans ape asc asm asp aspx avi awk"
+ " bas bat bmp"
+ " c cs cls clw cmd cpp csproj css ctl cxx"
+ " def dep dlg dsp dsw"
+ " eps"
+ " f f77 f90 f95 fla flac frm"
+ " gif"
+ " h hpp hta htm html hxx"
+ " ico idl inc ini inl"
+ " java jpeg jpg js"
+ " la"
+ " mak manifest wmv mov mp3 mp4 mpe mpeg mpg m4a"
+ " ofr ogg"
+ " pac pas pdf php php3 php4 php5 phptml pl pm png ps py pyo"
+ " ra rb rc reg rka rm rtf"
+ " sed sh shn shtml sln sql srt swa"
+ " tcl tex tiff tta txt"
+ " vb vcproj vbs"
+ " wav wma wv"
+ " xml xsd xsl xslt"
+ " ";
static bool DoNeedExtract(const UString &name)
{
@@ -345,9 +342,16 @@ static bool DoNeedExtract(const UString &name)
return true;
UString ext = name.Mid(extPos + 1);
ext.MakeLower();
- for (int i = 0; i < sizeof(kExtractExludeExtensions) / sizeof(kExtractExludeExtensions[0]); i++)
- if (ext.Compare(kExtractExludeExtensions[i]) == 0)
+ AString ext2 = UnicodeStringToMultiByte(ext);
+ const char *p = kExtractExludeExtensions;
+ for (int i = 0; p[i] != 0;)
+ {
+ int j;
+ for (j = i; p[j] != ' '; j++);
+ if (ext2.Length() == j - i && memcmp(p + i, (const char *)ext2, ext2.Length()) == 0)
return false;
+ i = j + 1;
+ }
return true;
}
@@ -402,7 +406,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
NFile::NDirectory::GetOnlyDirPrefix(fileName, folderPrefix);
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(fileName, fileInfo))
+ if (!fileInfo.Find(fileName))
return E_FAIL;
if (!fileInfo.IsDir() && DoNeedExtract(fileInfo.Name))
{
@@ -423,7 +427,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
for(int i = 0; i < _fileNames.Size(); i++)
{
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(_fileNames[i], fileInfo))
+ if (!fileInfo.Find(_fileNames[i]))
return E_FAIL;
if (!fileInfo.IsDir() && DoNeedExtract(fileInfo.Name))
needExtract = true;
@@ -434,7 +438,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
UString folderPrefix;
NFile::NDirectory::GetOnlyDirPrefix(fileName, folderPrefix);
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(fileName, fileInfo))
+ if (!fileInfo.Find(fileName))
return E_FAIL;
// Extract
if ((contextMenuFlags & NContextMenuFlags::kExtract) != 0)
diff --git a/CPP/7zip/UI/Explorer/Explorer.dsp b/CPP/7zip/UI/Explorer/Explorer.dsp
index a4c99ed6..832a153a 100755
--- a/CPP/7zip/UI/Explorer/Explorer.dsp
+++ b/CPP/7zip/UI/Explorer/Explorer.dsp
@@ -198,6 +198,14 @@ SOURCE=..\Common\CompressCall.h
# End Source File
# Begin Source File
+SOURCE=..\Common\ExtractingFilePath.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\Common\ExtractingFilePath.h
+# End Source File
+# Begin Source File
+
SOURCE=..\Common\ZipRegistry.cpp
# End Source File
# Begin Source File
diff --git a/CPP/7zip/UI/Explorer/makefile b/CPP/7zip/UI/Explorer/makefile
index ab9aff10..d9366ffe 100755
--- a/CPP/7zip/UI/Explorer/makefile
+++ b/CPP/7zip/UI/Explorer/makefile
@@ -49,6 +49,7 @@ WIN_CTRL_OBJS = \
UI_COMMON_OBJS = \
$O\ArchiveName.obj \
$O\CompressCall.obj \
+ $O\ExtractingFilePath.obj \
$O\ZipRegistry.obj \
FM_COMMON_OBJS = \
diff --git a/CPP/7zip/UI/Far/ExtractEngine.cpp b/CPP/7zip/UI/Far/ExtractEngine.cpp
index 55994ed6..677cac79 100755
--- a/CPP/7zip/UI/Far/ExtractEngine.cpp
+++ b/CPP/7zip/UI/Far/ExtractEngine.cpp
@@ -2,15 +2,9 @@
#include "StdAfx.h"
-#include <stdio.h>
-
-#include "ExtractEngine.h"
-
-#include "Common/Wildcard.h"
#include "Common/StringConvert.h"
-#include "Windows/Defs.h"
-
+#include "ExtractEngine.h"
#include "FarUtils.h"
#include "Messages.h"
#include "OverwriteDialog.h"
@@ -60,7 +54,7 @@ STDMETHODIMP CExtractCallBackImp::SetCompleted(const UInt64 *completeValue)
STDMETHODIMP CExtractCallBackImp::AskOverwrite(
const wchar_t *existName, const FILETIME *existTime, const UInt64 *existSize,
const wchar_t *newName, const FILETIME *newTime, const UInt64 *newSize,
- INT32 *answer)
+ Int32 *answer)
{
NOverwriteDialog::CFileInfo oldFileInfo, newFileInfo;
oldFileInfo.Time = *existTime;
@@ -108,7 +102,7 @@ STDMETHODIMP CExtractCallBackImp::AskOverwrite(
return S_OK;
}
-STDMETHODIMP CExtractCallBackImp::PrepareOperation(const wchar_t *name, bool /* isFolder */, INT32 /* askExtractMode */, const UInt64 * /* position */)
+STDMETHODIMP CExtractCallBackImp::PrepareOperation(const wchar_t *name, bool /* isFolder */, Int32 /* askExtractMode */, const UInt64 * /* position */)
{
if (WasEscPressed())
return E_ABORT;
@@ -124,7 +118,7 @@ STDMETHODIMP CExtractCallBackImp::MessageError(const wchar_t *message)
return S_OK;
}
-STDMETHODIMP CExtractCallBackImp::SetOperationResult(INT32 operationResult, bool encrypted)
+STDMETHODIMP CExtractCallBackImp::SetOperationResult(Int32 operationResult, bool encrypted)
{
switch(operationResult)
{
diff --git a/CPP/7zip/UI/Far/ExtractEngine.h b/CPP/7zip/UI/Far/ExtractEngine.h
index 62486fb1..5676103a 100755
--- a/CPP/7zip/UI/Far/ExtractEngine.h
+++ b/CPP/7zip/UI/Far/ExtractEngine.h
@@ -27,11 +27,11 @@ public:
STDMETHOD(AskOverwrite)(
const wchar_t *existName, const FILETIME *existTime, const UInt64 *existSize,
const wchar_t *newName, const FILETIME *newTime, const UInt64 *newSize,
- INT32 *result);
- STDMETHOD (PrepareOperation)(const wchar_t *name, bool isFolder, INT32 askExtractMode, const UInt64 *position);
+ Int32 *result);
+ STDMETHOD (PrepareOperation)(const wchar_t *name, bool isFolder, Int32 askExtractMode, const UInt64 *position);
STDMETHOD(MessageError)(const wchar_t *message);
- STDMETHOD(SetOperationResult)(INT32 resultEOperationResult, bool encrypted);
+ STDMETHOD(SetOperationResult)(Int32 resultEOperationResult, bool encrypted);
// ICryptoGetTextPassword
STDMETHOD(CryptoGetTextPassword)(BSTR *password);
@@ -44,15 +44,6 @@ private:
UString m_CurrentFilePath;
- /*
- struct CProcessedFileInfo
- {
- FILETIME MTime;
- bool isDir;
- UINT32 Attributes;
- } m_ProcessedFileInfo;
- */
-
CProgressBox *m_ProgressBox;
UINT m_CodePage;
diff --git a/CPP/7zip/UI/Far/Far.dsp b/CPP/7zip/UI/Far/Far.dsp
index 7bb43ef7..229035f9 100755
--- a/CPP/7zip/UI/Far/Far.dsp
+++ b/CPP/7zip/UI/Far/Far.dsp
@@ -118,6 +118,10 @@ SOURCE=.\StdAfx.h
# PROP Default_Filter ""
# Begin Source File
+SOURCE=..\..\..\Common\CRC.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\Common\IntToString.cpp
# End Source File
# Begin Source File
@@ -566,6 +570,15 @@ SOURCE=..\..\Common\StreamUtils.h
# PROP Default_Filter ""
# Begin Source File
+SOURCE=..\..\..\..\C\7zCrc.c
+# SUBTRACT CPP /YX /Yc /Yu
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\..\..\C\7zCrc.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\..\..\C\Alloc.c
# SUBTRACT CPP /YX /Yc /Yu
# End Source File
@@ -592,5 +605,17 @@ SOURCE=..\..\..\..\C\Threads.c
SOURCE=..\..\..\..\C\Threads.h
# End Source File
# End Group
+# Begin Group "Arc Common"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.h
+# End Source File
+# End Group
# End Target
# End Project
diff --git a/CPP/7zip/UI/Far/Main.cpp b/CPP/7zip/UI/Far/Main.cpp
index f042a785..46a16a9f 100755
--- a/CPP/7zip/UI/Far/Main.cpp
+++ b/CPP/7zip/UI/Far/Main.cpp
@@ -173,11 +173,10 @@ public:
}
void ShowMessage();
- void LoadFileInfo(const UString &folderPrefix,
- const UString &fileName)
+ void LoadFileInfo(const UString &folderPrefix, const UString &fileName)
{
_folderPrefix = folderPrefix;
- if (!NWindows::NFile::NFind::FindFile(_folderPrefix + fileName, _fileInfo))
+ if (!_fileInfo.Find(_folderPrefix + fileName))
throw 1;
}
};
@@ -297,7 +296,7 @@ STDMETHODIMP COpenArchiveCallback::GetStream(const wchar_t *name,
return E_ABORT;
*inStream = NULL;
UString fullPath = _folderPrefix + name;
- if (!NWindows::NFile::NFind::FindFile(fullPath, _fileInfo))
+ if (!_fileInfo.Find(fullPath))
return S_FALSE;
if (_fileInfo.IsDir())
return S_FALSE;
@@ -386,7 +385,7 @@ static HANDLE MyOpenFilePlugin(const char *name)
int fileNamePartStartIndex;
NFile::NDirectory::MyGetFullPathName(normalizedName, fullName, fileNamePartStartIndex);
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(fullName, fileInfo))
+ if (!fileInfo.Find(fullName))
return INVALID_HANDLE_VALUE;
if (fileInfo.IsDir())
return INVALID_HANDLE_VALUE;
@@ -415,7 +414,7 @@ static HANDLE MyOpenFilePlugin(const char *name)
archiveHandler = new CAgent;
CMyComBSTR archiveType;
- HRESULT result = archiveHandler->Open(
+ HRESULT result = archiveHandler->Open(NULL,
GetUnicodeString(fullName, CP_OEMCP), &archiveType, openArchiveCallback);
/*
HRESULT result = ::OpenArchive(fullName, &archiveHandler,
diff --git a/CPP/7zip/UI/Far/Messages.h b/CPP/7zip/UI/Far/Messages.h
index 1281b235..9c7c69fb 100755
--- a/CPP/7zip/UI/Far/Messages.h
+++ b/CPP/7zip/UI/Far/Messages.h
@@ -64,6 +64,17 @@ enum EEnum
kChecksum,
kCharacts,
kVa,
+ kId,
+ kShortName,
+ kCreatorApp,
+ kSectorSize,
+ kPosixAttrib,
+ kLink,
+
+ kTotalSize,
+ kFreeSpace,
+ kClusterSize,
+ kLabel,
kGetPasswordTitle,
kEnterPasswordForFile,
diff --git a/CPP/7zip/UI/Far/Plugin.cpp b/CPP/7zip/UI/Far/Plugin.cpp
index dc2a3ed1..c1e45a62 100755
--- a/CPP/7zip/UI/Far/Plugin.cpp
+++ b/CPP/7zip/UI/Far/Plugin.cpp
@@ -21,17 +21,14 @@ using namespace NWindows;
using namespace NFar;
CPlugin::CPlugin(const UString &fileName,
- // const UString &defaultName,
IInFolderArchive *archiveHandler,
UString archiveTypeName
):
m_ArchiveHandler(archiveHandler),
m_FileName(fileName),
_archiveTypeName(archiveTypeName)
- // , m_DefaultName(defaultName)
- // , m_ArchiverInfo(archiverInfo)
{
- if (!NFile::NFind::FindFile(m_FileName, m_FileInfo))
+ if (!m_FileInfo.Find(m_FileName))
throw "error";
archiveHandler->BindToRootFolder(&_folder);
}
@@ -324,7 +321,18 @@ static CPROPIDToName kPROPIDToName[] =
{ kpidHeadersSize, NMessageID::kHeadersSize },
{ kpidChecksum, NMessageID::kChecksum },
{ kpidCharacts, NMessageID::kCharacts },
- { kpidVa, NMessageID::kVa }
+ { kpidVa, NMessageID::kVa },
+ { kpidId, NMessageID::kId },
+ { kpidShortName, NMessageID::kShortName},
+ { kpidCreatorApp, NMessageID::kCreatorApp },
+ { kpidSectorSize, NMessageID::kSectorSize },
+ { kpidPosixAttrib, NMessageID::kPosixAttrib },
+ { kpidLink, NMessageID::kLink },
+
+ { kpidTotalSize, NMessageID::kTotalSize },
+ { kpidFreeSpace, NMessageID::kFreeSpace },
+ { kpidClusterSize, NMessageID::kClusterSize },
+ { kpidVolumeName, NMessageID::kLabel }
};
static const int kNumPROPIDToName = sizeof(kPROPIDToName) / sizeof(kPROPIDToName[0]);
diff --git a/CPP/7zip/UI/Far/Plugin.h b/CPP/7zip/UI/Far/Plugin.h
index 034b1556..06003ba5 100755
--- a/CPP/7zip/UI/Far/Plugin.h
+++ b/CPP/7zip/UI/Far/Plugin.h
@@ -40,7 +40,6 @@ class CPlugin
void GetCurrentDir();
public:
UString m_FileName;
- // UString m_DefaultName;
NWindows::NFile::NFind::CFileInfoW m_FileInfo;
CMyComPtr<IInFolderArchive> m_ArchiveHandler;
diff --git a/CPP/7zip/UI/Far/PluginWrite.cpp b/CPP/7zip/UI/Far/PluginWrite.cpp
index 2f7fbc83..44c6fecd 100755
--- a/CPP/7zip/UI/Far/PluginWrite.cpp
+++ b/CPP/7zip/UI/Far/PluginWrite.cpp
@@ -683,7 +683,7 @@ HRESULT CompressFiles(const CObjectVector<PluginPanelItem> &pluginPanelItems)
CMyComPtr<IOutFolderArchive> outArchive;
CMyComPtr<IInFolderArchive> archiveHandler;
- if(NFind::FindFile(fullArchiveName, fileInfo))
+ if(fileInfo.Find(fullArchiveName))
{
if (fileInfo.IsDir())
throw "There is Directory with such name";
@@ -692,7 +692,7 @@ HRESULT CompressFiles(const CObjectVector<PluginPanelItem> &pluginPanelItems)
archiveHandler = agentSpec;
// CLSID realClassID;
CMyComBSTR archiveType;
- RINOK(agentSpec->Open(
+ RINOK(agentSpec->Open(NULL,
GetUnicodeString(fullArchiveName, CP_OEMCP),
// &realClassID,
&archiveType,
diff --git a/CPP/7zip/UI/Far/UpdateCallback100.cpp b/CPP/7zip/UI/Far/UpdateCallback100.cpp
index dc90c810..0785f55b 100755
--- a/CPP/7zip/UI/Far/UpdateCallback100.cpp
+++ b/CPP/7zip/UI/Far/UpdateCallback100.cpp
@@ -52,3 +52,15 @@ STDMETHODIMP CUpdateCallback100Imp::UpdateErrorMessage(const wchar_t *message)
return S_OK;
}
+extern HRESULT GetPassword(UString &password);
+
+STDMETHODIMP CUpdateCallback100Imp::CryptoGetTextPassword(BSTR *password)
+{
+ *password = NULL;
+ if (!m_PasswordIsDefined)
+ {
+ RINOK(GetPassword(m_Password));
+ m_PasswordIsDefined = true;
+ }
+ return StringToBstr(m_Password, password);
+}
diff --git a/CPP/7zip/UI/Far/UpdateCallback100.h b/CPP/7zip/UI/Far/UpdateCallback100.h
index 45f4daea..bfe8419a 100755
--- a/CPP/7zip/UI/Far/UpdateCallback100.h
+++ b/CPP/7zip/UI/Far/UpdateCallback100.h
@@ -1,33 +1,40 @@
// UpdateCallback.h
-#ifndef __UPDATECALLBACK100_H
-#define __UPDATECALLBACK100_H
+#ifndef __UPDATE_CALLBACK_H
+#define __UPDATE_CALLBACK_H
#include "Common/MyCom.h"
#include "../Agent/IFolderArchive.h"
+#include "../../IPassword.h"
+
#include "ProgressBox.h"
class CUpdateCallback100Imp:
public IFolderArchiveUpdateCallback,
+ public ICryptoGetTextPassword,
public CMyUnknownImp
{
// CMyComPtr<IInFolderArchive> _archiveHandler;
CProgressBox *_progressBox;
UInt64 _total;
+ bool m_PasswordIsDefined;
+ UString m_Password;
public:
- MY_UNKNOWN_IMP
+ MY_UNKNOWN_IMP1(ICryptoGetTextPassword)
INTERFACE_IProgress(;)
INTERFACE_IFolderArchiveUpdateCallback(;)
+ STDMETHOD(CryptoGetTextPassword)(BSTR *password);
CUpdateCallback100Imp(): _total(0) {}
void Init(/* IInFolderArchive *archiveHandler, */ CProgressBox *progressBox)
{
// _archiveHandler = archiveHandler;
_progressBox = progressBox;
+ m_PasswordIsDefined = false;
}
};
diff --git a/CPP/7zip/UI/Far/makefile b/CPP/7zip/UI/Far/makefile
index dba62d63..01c77ded 100755
--- a/CPP/7zip/UI/Far/makefile
+++ b/CPP/7zip/UI/Far/makefile
@@ -64,6 +64,9 @@ UI_COMMON_OBJS = \
$O\WorkDir.obj \
$O\ZipRegistry.obj \
+AR_COMMON_OBJS = \
+ $O\OutStreamWithCRC.obj \
+
AGENT_OBJS = \
$O\Agent.obj \
$O\AgentOut.obj \
@@ -75,6 +78,8 @@ C_OBJS = \
$O\Sort.obj \
$O\Threads.obj \
+!include "../../Crc2.mak"
+
OBJS = \
$O\StdAfx.obj \
$(FAR_OBJS) \
@@ -82,9 +87,11 @@ OBJS = \
$(WIN_OBJS) \
$(7ZIP_COMMON_OBJS) \
$(UI_COMMON_OBJS) \
+ $(AR_COMMON_OBJS) \
$(AGENT_OBJS) \
$(C_OBJS) \
$O\CopyCoder.obj \
+ $(CRC_OBJS) \
$O\resource.res
!include "../../../Build.mak"
@@ -99,9 +106,12 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(UI_COMMON_OBJS): ../Common/$(*B).cpp
$(COMPL)
+$(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
+ $(COMPL)
$(AGENT_OBJS): ../Agent/$(*B).cpp
$(COMPL)
$O\CopyCoder.obj: ../../Compress/$(*B).cpp
$(COMPL)
$(C_OBJS): ../../../../C/$(*B).c
$(COMPL_O2)
+!include "../../Crc.mak"
diff --git a/CPP/7zip/UI/FileManager/App.cpp b/CPP/7zip/UI/FileManager/App.cpp
index f4f0bde7..21942065 100755
--- a/CPP/7zip/UI/FileManager/App.cpp
+++ b/CPP/7zip/UI/FileManager/App.cpp
@@ -157,12 +157,12 @@ static void CreateToolbar(
struct CButtonInfo
{
- UINT commandID;
+ int CommandID;
UINT BitmapResID;
UINT Bitmap2ResID;
UINT StringResID;
- UINT32 LangID;
- UString GetText()const { return LangString(StringResID, LangID); };
+ UInt32 LangID;
+ UString GetText() const { return LangString(StringResID, LangID); };
};
static CButtonInfo g_StandardButtons[] =
@@ -180,12 +180,12 @@ static CButtonInfo g_ArchiveButtons[] =
{ kTestCommand , IDB_TEST, IDB_TEST2, IDS_TEST, 0x03020402}
};
-bool SetButtonText(UINT32 commandID, CButtonInfo *buttons, int numButtons, UString &s)
+static bool SetButtonText(int commandID, CButtonInfo *buttons, int numButtons, UString &s)
{
for (int i = 0; i < numButtons; i++)
{
const CButtonInfo &b = buttons[i];
- if (b.commandID == commandID)
+ if (b.CommandID == commandID)
{
s = b.GetText();
return true;
@@ -194,7 +194,7 @@ bool SetButtonText(UINT32 commandID, CButtonInfo *buttons, int numButtons, UStri
return false;
}
-void SetButtonText(UINT32 commandID, UString &s)
+static void SetButtonText(int commandID, UString &s)
{
if (SetButtonText(commandID, g_StandardButtons,
sizeof(g_StandardButtons) / sizeof(g_StandardButtons[0]), s))
@@ -212,7 +212,7 @@ static void AddButton(
{
TBBUTTON but;
but.iBitmap = 0;
- but.idCommand = butInfo.commandID;
+ but.idCommand = butInfo.CommandID;
but.fsState = TBSTATE_ENABLED;
but.fsStyle = BTNS_BUTTON
// | BTNS_AUTOSIZE
@@ -428,20 +428,12 @@ void CApp::Release()
Panels[i].Release();
}
-static bool IsThereFolderOfPath(const UString &path)
-{
- CFileInfoW fi;
- if (!FindFile(path, fi))
- return false;
- return fi.IsDir();
-}
-
// reduces path to part that exists on disk
static void ReducePathToRealFileSystemPath(UString &path)
{
while (!path.IsEmpty())
{
- if (IsThereFolderOfPath(path))
+ if (NFind::DoesDirExist(path))
{
NName::NormalizeDirPathPrefix(path);
break;
@@ -663,7 +655,7 @@ void CApp::OnCopy(bool move, bool copyToSame, int srcPanelIndex)
}
if (indices.Size() > 1 || (destPath.Length() > 0 && destPath.ReverseFind(WCHAR_PATH_SEPARATOR) == destPath.Length() - 1) ||
- IsThereFolderOfPath(destPath))
+ NFind::DoesDirExist(destPath))
{
NDirectory::CreateComplexDirectory(destPath);
NName::NormalizeDirPathPrefix(destPath);
@@ -698,7 +690,15 @@ void CApp::OnCopy(bool move, bool copyToSame, int srcPanelIndex)
SaveCopyHistory(copyFolders);
}
- bool useSrcPanel = (!useDestPanel || !srcPanel.IsFSFolder() || destPanel.IsFSFolder());
+ /*
+ if (destPath == destPanel._currentFolderPrefix)
+ {
+ if (destPanel.GetFolderTypeID() == L"PhysDrive")
+ useDestPanel = true;
+ }
+ */
+
+ bool useSrcPanel = (!useDestPanel || !srcPanel.IsFsOrDrivesFolder() || destPanel.IsFSFolder());
bool useTemp = useSrcPanel && useDestPanel;
NFile::NDirectory::CTempDirectoryW tempDirectory;
UString tempDirPrefix;
@@ -857,7 +857,7 @@ void CApp::OnNotify(int /* ctrlID */, LPNMHDR pnmh)
LPNMTTDISPINFO info = (LPNMTTDISPINFO)pnmh;
info->hinst = 0;
g_ToolTipBuffer.Empty();
- SetButtonText((UINT32)info->hdr.idFrom, g_ToolTipBuffer);
+ SetButtonText((int)info->hdr.idFrom, g_ToolTipBuffer);
g_ToolTipBufferSys = GetSystemString(g_ToolTipBuffer);
info->lpszText = (LPTSTR)(LPCTSTR)g_ToolTipBufferSys;
return;
@@ -868,7 +868,7 @@ void CApp::OnNotify(int /* ctrlID */, LPNMHDR pnmh)
LPNMTTDISPINFOW info = (LPNMTTDISPINFOW)pnmh;
info->hinst = 0;
g_ToolTipBuffer.Empty();
- SetButtonText((UINT32)info->hdr.idFrom, g_ToolTipBuffer);
+ SetButtonText((int)info->hdr.idFrom, g_ToolTipBuffer);
info->lpszText = (LPWSTR)(LPCWSTR)g_ToolTipBuffer;
return;
}
@@ -893,4 +893,3 @@ void CApp::RefreshTitle(int panelIndex, bool always)
return;
RefreshTitle(always);
}
-
diff --git a/CPP/7zip/UI/FileManager/App.h b/CPP/7zip/UI/FileManager/App.h
index d30e1151..1fc77138 100755
--- a/CPP/7zip/UI/FileManager/App.h
+++ b/CPP/7zip/UI/FileManager/App.h
@@ -204,6 +204,7 @@ public:
void Delete(bool toRecycleBin)
{ GetFocusedPanel().DeleteItems(toRecycleBin); }
void CalculateCrc();
+ void DiffFiles();
void Split();
void Combine();
void Properties()
diff --git a/CPP/7zip/UI/FileManager/AppState.h b/CPP/7zip/UI/FileManager/AppState.h
index 5ba0d47f..4f8b7bbe 100755
--- a/CPP/7zip/UI/FileManager/AppState.h
+++ b/CPP/7zip/UI/FileManager/AppState.h
@@ -1,10 +1,12 @@
// AppState.h
-#ifndef __APPSTATE_H
-#define __APPSTATE_H
+#ifndef __APP_STATE_H
+#define __APP_STATE_H
#include "Windows/Synchronization.h"
+#include "ViewSettings.h"
+
void inline AddUniqueStringToHead(UStringVector &list,
const UString &string)
{
diff --git a/CPP/7zip/UI/FileManager/ExtractCallback.cpp b/CPP/7zip/UI/FileManager/ExtractCallback.cpp
index b5e70d02..9902e9a1 100755
--- a/CPP/7zip/UI/FileManager/ExtractCallback.cpp
+++ b/CPP/7zip/UI/FileManager/ExtractCallback.cpp
@@ -2,27 +2,26 @@
#include "StdAfx.h"
-#include "ExtractCallback.h"
+#include "Common/Wildcard.h"
+#include "Common/StringConvert.h"
#include "Windows/Error.h"
-#include "Windows/FileFind.h"
#include "Windows/FileDir.h"
+#include "Windows/FileFind.h"
#include "Windows/ResourceString.h"
-#include "OverwriteDialog.h"
-#ifndef _NO_CRYPTO
-#include "PasswordDialog.h"
-#endif
-#include "MessagesDialog.h"
+#include "../../Common/FilePathAutoRename.h"
+
#include "../GUI/ExtractRes.h"
#include "../GUI/resource.h"
-#include "Common/Wildcard.h"
-#include "Common/StringConvert.h"
-
+#include "ExtractCallback.h"
#include "FormatUtils.h"
-
-#include "../../Common/FilePathAutoRename.h"
+#include "MessagesDialog.h"
+#include "OverwriteDialog.h"
+#ifndef _NO_CRYPTO
+#include "PasswordDialog.h"
+#endif
using namespace NWindows;
using namespace NFile;
@@ -351,6 +350,8 @@ HRESULT CExtractCallbackImp::ExtractResult(HRESULT result)
return S_OK;
}
+#ifndef _NO_CRYPTO
+
HRESULT CExtractCallbackImp::SetPassword(const UString &password)
{
PasswordIsDefined = true;
@@ -372,6 +373,7 @@ STDMETHODIMP CExtractCallbackImp::CryptoGetTextPassword(BSTR *password)
return StringToBstr(Password, password);
}
+#endif
// IExtractCallBack3
STDMETHODIMP CExtractCallbackImp::AskWrite(
@@ -392,7 +394,7 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
UString destPathSys = destPathSpec;
bool srcIsFolderSpec = IntToBool(srcIsFolder);
CFileInfoW destFileInfo;
- if (FindFile(destPathSys, destFileInfo))
+ if (destFileInfo.Find(destPathSys))
{
if (srcIsFolderSpec)
{
@@ -474,4 +476,3 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
*writeAnswer = BoolToInt(true);
return StringToBstr(destPathResultTemp, destPathResult);
}
-
diff --git a/CPP/7zip/UI/FileManager/FM.cpp b/CPP/7zip/UI/FileManager/FM.cpp
index fc94bcbf..e4bcc998 100755
--- a/CPP/7zip/UI/FileManager/FM.cpp
+++ b/CPP/7zip/UI/FileManager/FM.cpp
@@ -2,40 +2,28 @@
#include "StdAfx.h"
-#include "resource.h"
-#include "Panel.h"
-
-extern "C"
-{
- #include "../../../../C/Alloc.h"
-}
+#include "../../../../C/Alloc.h"
-#include "Common/Defs.h"
-#include "Common/StringConvert.h"
-// #include "Common/CommandLineParser.h"
-
-#include "Windows/Control/Toolbar.h"
#include "Windows/Error.h"
-#include "Windows/COM.h"
-#include "Windows/DLL.h"
-#include "Windows/Security.h"
#include "Windows/MemoryLock.h"
+#include "Windows/Security.h"
-#include "ViewSettings.h"
#include "../GUI/ExtractRes.h"
-#include "App.h"
-#include "StringUtils.h"
+#include "resource.h"
-#include "MyLoadMenu.h"
-#include "LangUtils.h"
+#include "App.h"
#include "FormatUtils.h"
+#include "LangUtils.h"
+#include "MyLoadMenu.h"
+#include "Panel.h"
#include "RegistryUtils.h"
+#include "StringUtils.h"
+#include "ViewSettings.h"
using namespace NWindows;
using namespace NFile;
using namespace NFind;
-// using namespace NCommandLineParser;
#define MAX_LOADSTRING 100
@@ -617,10 +605,8 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
bool needOpenFile = false;
if (!g_MainPath.IsEmpty() /* && g_OpenArchive */)
{
- NFile::NFind::CFileInfoW fileInfo;
- if (NFile::NFind::FindFile(g_MainPath, fileInfo))
- if (!fileInfo.IsDir())
- needOpenFile = true;
+ if (NFile::NFind::DoesFileExist(g_MainPath))
+ needOpenFile = true;
}
HRESULT res = g_App.Create(hWnd, g_MainPath, xSizes, archiveIsOpened, encrypted);
diff --git a/CPP/7zip/UI/FileManager/FM.dsp b/CPP/7zip/UI/FileManager/FM.dsp
index 6727b085..2c3ab6c8 100755
--- a/CPP/7zip/UI/FileManager/FM.dsp
+++ b/CPP/7zip/UI/FileManager/FM.dsp
@@ -45,7 +45,7 @@ RSC=rc.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "NDEBUG"
@@ -72,7 +72,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /GZ /c
-# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "_DEBUG"
@@ -99,7 +99,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MD /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"StdAfx.h" /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /Yu"StdAfx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "NDEBUG"
@@ -127,7 +127,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"StdAfx.h" /FD /GZ /c
-# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /Yu"StdAfx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "WIN_LONG_PATH" /D "NEW_FOLDER_INTERFACE" /D "EXTERNAL_CODECS" /D "SUPPORT_DEVICE_FILE" /Yu"StdAfx.h" /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "_DEBUG"
@@ -210,13 +210,21 @@ SOURCE=.\StdAfx.h
SOURCE=.\Test.bmp
# End Source File
# End Group
-# Begin Group "Archive Interfaces"
+# Begin Group "Archive"
# PROP Default_Filter ""
# Begin Source File
SOURCE=..\..\Archive\IArchive.h
# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.h
+# End Source File
# End Group
# Begin Group "Folders"
@@ -255,14 +263,6 @@ SOURCE=.\NetFolder.h
# End Source File
# Begin Source File
-SOURCE=.\PhysDriveFolder.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=.\PhysDriveFolder.h
-# End Source File
-# Begin Source File
-
SOURCE=.\RootFolder.cpp
# End Source File
# Begin Source File
@@ -831,14 +831,6 @@ SOURCE=..\..\..\Windows\Error.h
# End Source File
# Begin Source File
-SOURCE=..\..\..\Windows\FileDevice.cpp
-# End Source File
-# Begin Source File
-
-SOURCE=..\..\..\Windows\FileDevice.h
-# End Source File
-# Begin Source File
-
SOURCE=..\..\..\Windows\FileDir.cpp
# End Source File
# Begin Source File
diff --git a/CPP/7zip/UI/FileManager/FSDrives.cpp b/CPP/7zip/UI/FileManager/FSDrives.cpp
index f2d7ac93..87ee3fc9 100755
--- a/CPP/7zip/UI/FileManager/FSDrives.cpp
+++ b/CPP/7zip/UI/FileManager/FSDrives.cpp
@@ -2,48 +2,118 @@
#include "StdAfx.h"
-#include "resource.h"
-
-#include "FSDrives.h"
+#include "../../../../C/Alloc.h"
-#include "Common/StringConvert.h"
#include "Common/ComTry.h"
-#include "../../PropID.h"
+#include "Common/StringConvert.h"
+
#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
#include "Windows/FileDir.h"
+#include "Windows/FileIO.h"
#include "Windows/FileSystem.h"
+#include "Windows/PropVariant.h"
-#include "SysIconUtils.h"
+#include "../../PropID.h"
+
+#include "FSDrives.h"
#include "FSFolder.h"
-#include "PhysDriveFolder.h"
#include "LangUtils.h"
+#include "SysIconUtils.h"
+
+#include "resource.h"
using namespace NWindows;
using namespace NFile;
using namespace NFind;
-static const STATPROPSTG kProperties[] =
+static const wchar_t *kVolPrefix = L"\\\\.\\";
+
+UString CDriveInfo::GetDeviceFileIoName() const
+{
+ return kVolPrefix + Name;
+}
+
+struct CPhysTempBuffer
+{
+ void *buffer;
+ CPhysTempBuffer(): buffer(0) {}
+ ~CPhysTempBuffer() { MidFree(buffer); }
+};
+
+static HRESULT CopyFileSpec(LPCWSTR fromPath, LPCWSTR toPath, bool writeToDisk, UInt64 fileSize,
+ UInt32 bufferSize, UInt64 progressStart, IProgress *progress)
+{
+ NFile::NIO::CInFile inFile;
+ if (!inFile.Open(fromPath))
+ return GetLastError();
+ if (fileSize == (UInt64)(Int64)-1)
+ {
+ if (!inFile.GetLength(fileSize))
+ ::GetLastError();
+ }
+ NFile::NIO::COutFile outFile;
+ if (writeToDisk)
+ {
+ if (!outFile.Open(toPath, FILE_SHARE_WRITE, OPEN_EXISTING, 0))
+ return GetLastError();
+ }
+ else
+ if (!outFile.Create(toPath, true))
+ return GetLastError();
+ CPhysTempBuffer tempBuffer;
+ tempBuffer.buffer = MidAlloc(bufferSize);
+ if (tempBuffer.buffer == 0)
+ return E_OUTOFMEMORY;
+
+ for (UInt64 pos = 0; pos < fileSize;)
+ {
+ UInt64 progressCur = progressStart + pos;
+ RINOK(progress->SetCompleted(&progressCur));
+ UInt64 rem = fileSize - pos;
+ UInt32 curSize = (UInt32)MyMin(rem, (UInt64)bufferSize);
+ UInt32 processedSize;
+ if (!inFile.Read(tempBuffer.buffer, curSize, processedSize))
+ return GetLastError();
+ if (processedSize == 0)
+ break;
+ curSize = processedSize;
+ if (writeToDisk)
+ {
+ const UInt32 kMask = 0x1FF;
+ curSize = (curSize + kMask) & ~kMask;
+ if (curSize > bufferSize)
+ return E_FAIL;
+ }
+
+ if (!outFile.Write(tempBuffer.buffer, curSize, processedSize))
+ return GetLastError();
+ if (curSize != processedSize)
+ return E_FAIL;
+ pos += curSize;
+ }
+ return S_OK;
+}
+
+static const STATPROPSTG kProps[] =
{
{ NULL, kpidName, VT_BSTR},
- // { NULL, kpidIsDir, VT_BOOL},
- { L"Total Size", kpidTotalSize, VT_UI8},
- { L"Free Space", kpidFreeSpace, VT_UI8},
+ { NULL, kpidTotalSize, VT_UI8},
+ { NULL, kpidFreeSpace, VT_UI8},
{ NULL, kpidType, VT_BSTR},
- { L"Label", kpidVolumeName, VT_BSTR},
- { L"File system", kpidFileSystem, VT_BSTR},
- { L"Cluster Size", kpidClusterSize, VT_UI8}
+ { NULL, kpidVolumeName, VT_BSTR},
+ { NULL, kpidFileSystem, VT_BSTR},
+ { NULL, kpidClusterSize, VT_UI8}
};
-static const wchar_t *kDriveTypes[] =
+static const char *kDriveTypes[] =
{
- L"Unknown",
- L"No Root Dir",
- L"Removable",
- L"Fixed",
- L"Remote",
- L"CD-ROM",
- L"RAM disk"
+ "Unknown",
+ "No Root Dir",
+ "Removable",
+ "Fixed",
+ "Remote",
+ "CD-ROM",
+ "RAM disk"
};
STDMETHODIMP CFSDrives::LoadItems()
@@ -60,18 +130,13 @@ STDMETHODIMP CFSDrives::LoadItems()
di.FullSystemName = driveName;
- di.Name = di.FullSystemName.Left(
- di.FullSystemName.Length() - 1);
+ di.Name = di.FullSystemName.Left(di.FullSystemName.Length() - 1);
di.ClusterSize = 0;
di.DriveSize = 0;
di.FreeSpace = 0;
- UINT driveType = NFile::NSystem::MyGetDriveType(driveName);
- if (driveType < sizeof(kDriveTypes) / sizeof(kDriveTypes[0]))
- {
- di.Type = kDriveTypes[driveType];
- }
+ di.DriveType = NFile::NSystem::MyGetDriveType(driveName);
bool needRead = true;
- if (driveType == DRIVE_CDROM || driveType == DRIVE_REMOVABLE)
+ if (di.DriveType == DRIVE_CDROM || di.DriveType == DRIVE_REMOVABLE)
{
/*
DWORD dwSerialNumber;`
@@ -117,12 +182,15 @@ STDMETHODIMP CFSDrives::GetProperty(UInt32 itemIndex, PROPID propID, PROPVARIANT
const CDriveInfo &di = _drives[itemIndex];
switch(propID)
{
- case kpidIsDir: prop = true; break;
+ case kpidIsDir: prop = !_volumeMode; break;
case kpidName: prop = di.Name; break;
case kpidTotalSize: if (di.KnownSizes) prop = di.DriveSize; break;
case kpidFreeSpace: if (di.KnownSizes) prop = di.FreeSpace; break;
case kpidClusterSize: if (di.KnownSizes) prop = di.ClusterSize; break;
- case kpidType: prop = di.Type; break;
+ case kpidType:
+ if (di.DriveType < sizeof(kDriveTypes) / sizeof(kDriveTypes[0]))
+ prop = kDriveTypes[di.DriveType];
+ break;
case kpidVolumeName: prop = di.VolumeName; break;
case kpidFileSystem: prop = di.FileSystemName; break;
}
@@ -133,6 +201,8 @@ STDMETHODIMP CFSDrives::GetProperty(UInt32 itemIndex, PROPID propID, PROPVARIANT
HRESULT CFSDrives::BindToFolderSpec(const wchar_t *name, IFolderFolder **resultFolder)
{
*resultFolder = 0;
+ if (_volumeMode)
+ return S_OK;
NFsFolder::CFSFolder *fsFolderSpec = new NFsFolder::CFSFolder;
CMyComPtr<IFolderFolder> subFolder = fsFolderSpec;
RINOK(fsFolderSpec->Init(name, 0));
@@ -146,6 +216,7 @@ STDMETHODIMP CFSDrives::BindToFolder(UInt32 index, IFolderFolder **resultFolder)
if (index >= (UInt32)_drives.Size())
return E_INVALIDARG;
const CDriveInfo &di = _drives[index];
+ /*
if (_volumeMode)
{
*resultFolder = 0;
@@ -155,6 +226,7 @@ STDMETHODIMP CFSDrives::BindToFolder(UInt32 index, IFolderFolder **resultFolder)
*resultFolder = subFolder.Detach();
return S_OK;
}
+ */
return BindToFolderSpec(di.FullSystemName, resultFolder);
}
@@ -169,24 +241,7 @@ STDMETHODIMP CFSDrives::BindToParentFolder(IFolderFolder **resultFolder)
return S_OK;
}
-STDMETHODIMP CFSDrives::GetNumberOfProperties(UInt32 *numProperties)
-{
- *numProperties = sizeof(kProperties) / sizeof(kProperties[0]);
- return S_OK;
-}
-
-STDMETHODIMP CFSDrives::GetPropertyInfo(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType)
-{
- if (index >= sizeof(kProperties) / sizeof(kProperties[0]))
- return E_INVALIDARG;
- const STATPROPSTG &prop = kProperties[index];
- *propID = prop.propid;
- *varType = prop.vt;
- *name = 0;
- return S_OK;
-}
-
+IMP_IFolderFolder_Props(CFSDrives)
STDMETHODIMP CFSDrives::GetFolderProperty(PROPID propID, PROPVARIANT *value)
{
@@ -195,14 +250,20 @@ STDMETHODIMP CFSDrives::GetFolderProperty(PROPID propID, PROPVARIANT *value)
switch(propID)
{
case kpidType: prop = L"FSDrives"; break;
- case kpidPath: prop = LangString(IDS_COMPUTER, 0x03020300) + UString(WCHAR_PATH_SEPARATOR); break;
+ case kpidPath:
+ if (_volumeMode)
+ prop = kVolPrefix;
+ else
+ prop = LangString(IDS_COMPUTER, 0x03020300) + UString(WCHAR_PATH_SEPARATOR);
+ break;
}
prop.Detach(value);
return S_OK;
COM_TRY_END
}
-STDMETHODIMP CFSDrives::GetSystemIconIndex(UInt32 index, INT32 *iconIndex)
+
+STDMETHODIMP CFSDrives::GetSystemIconIndex(UInt32 index, Int32 *iconIndex)
{
*iconIndex = 0;
const CDriveInfo &di = _drives[index];
@@ -215,3 +276,145 @@ STDMETHODIMP CFSDrives::GetSystemIconIndex(UInt32 index, INT32 *iconIndex)
return GetLastError();
}
+UString CFSDrives::GetExt(int index) const
+{
+ const CDriveInfo &di = _drives[index];
+ const wchar_t *ext = NULL;
+ if (di.DriveType == DRIVE_CDROM)
+ ext = L"iso";
+ else if (di.FileSystemName.Find(L"NTFS") >= 0)
+ ext = L"ntfs";
+ else if (di.FileSystemName.Find(L"FAT") >= 0)
+ ext = L"fat";
+ else
+ ext = L"img";
+ return (UString)L'.' + ext;
+}
+
+HRESULT CFSDrives::GetLength(int index, UInt64 &length) const
+{
+ NFile::NIO::CInFile inFile;
+ if (!inFile.Open(_drives[index].GetDeviceFileIoName()))
+ return GetLastError();
+ if (!inFile.LengthDefined)
+ return E_FAIL;
+ length = inFile.Length;
+ return S_OK;
+}
+
+STDMETHODIMP CFSDrives::CopyTo(const UInt32 *indices, UInt32 numItems,
+ const wchar_t *path, IFolderOperationsExtractCallback *callback)
+{
+ if (numItems == 0)
+ return S_OK;
+
+ if (!_volumeMode)
+ return E_NOTIMPL;
+
+ UInt64 totalSize = 0;
+ UInt32 i;
+ for (i = 0; i < numItems; i++)
+ {
+ const CDriveInfo &di = _drives[indices[i]];
+ if (di.KnownSizes)
+ totalSize += di.DriveSize;
+ }
+ RINOK(callback->SetTotal(totalSize));
+ RINOK(callback->SetNumFiles(numItems));
+
+ UString destPath = path;
+ if (destPath.IsEmpty())
+ return E_INVALIDARG;
+ bool directName = (destPath[destPath.Length() - 1] != WCHAR_PATH_SEPARATOR);
+ if (directName)
+ {
+ if (numItems > 1)
+ return E_INVALIDARG;
+ }
+
+ UInt64 completedSize = 0;
+ RINOK(callback->SetCompleted(&completedSize));
+ for (i = 0; i < numItems; i++)
+ {
+ int index = indices[i];
+ const CDriveInfo &di = _drives[index];
+ UString destPath2 = destPath;
+ UString name = di.Name;
+ if (!directName)
+ {
+ UString destName = name;
+ if (!destName.IsEmpty() && destName[destName.Length() - 1] == L':')
+ {
+ destName.Delete(destName.Length() - 1);
+ destName += GetExt(index);
+ }
+ destPath2 += destName;
+ }
+ UString srcPath = di.GetDeviceFileIoName();
+
+ UInt64 fileSize = 0;
+ if (GetLength(index, fileSize) != S_OK)
+ {
+ return E_FAIL;
+ }
+ if (!di.KnownSizes)
+ totalSize += fileSize;
+ RINOK(callback->SetTotal(totalSize));
+
+ Int32 writeAskResult;
+ CMyComBSTR destPathResult;
+ RINOK(callback->AskWrite(srcPath, BoolToInt(false), NULL, &fileSize,
+ destPath2, &destPathResult, &writeAskResult));
+ if (!IntToBool(writeAskResult))
+ continue;
+
+ RINOK(callback->SetCurrentFilePath(srcPath));
+
+ static const UInt32 kBufferSize = (4 << 20);
+ UInt32 bufferSize = (di.DriveType == DRIVE_REMOVABLE) ? (18 << 10) * 4 : kBufferSize;
+ RINOK(CopyFileSpec(srcPath, destPathResult, false, fileSize, bufferSize, completedSize, callback));
+ completedSize += fileSize;
+ }
+ return S_OK;
+}
+
+STDMETHODIMP CFSDrives::MoveTo(
+ const UInt32 * /* indices */,
+ UInt32 /* numItems */,
+ const wchar_t * /* path */,
+ IFolderOperationsExtractCallback * /* callback */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::CopyFrom(const wchar_t * /* fromFolderPath */,
+ const wchar_t ** /* itemsPaths */, UInt32 /* numItems */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::CreateFolder(const wchar_t * /* name */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::CreateFile(const wchar_t * /* name */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::Rename(UInt32 /* index */, const wchar_t * /* newName */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::Delete(const UInt32 * /* indices */, UInt32 /* numItems */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
+
+STDMETHODIMP CFSDrives::SetProperty(UInt32 /* index */, PROPID /* propID */,
+ const PROPVARIANT * /* value */, IProgress * /* progress */)
+{
+ return E_NOTIMPL;
+}
diff --git a/CPP/7zip/UI/FileManager/FSDrives.h b/CPP/7zip/UI/FileManager/FSDrives.h
index 84db5b7e..fc99bce7 100755
--- a/CPP/7zip/UI/FileManager/FSDrives.h
+++ b/CPP/7zip/UI/FileManager/FSDrives.h
@@ -1,13 +1,10 @@
// FSDrives.h
-#ifndef __FSDRIVES_H
-#define __FSDRIVES_H
+#ifndef __FS_DRIVES_H
+#define __FS_DRIVES_H
-#include "Common/MyString.h"
-#include "Common/Types.h"
#include "Common/MyCom.h"
-#include "Windows/FileFind.h"
-#include "Windows/PropVariant.h"
+#include "Common/MyString.h"
#include "IFolder.h"
@@ -19,31 +16,38 @@ struct CDriveInfo
UInt64 DriveSize;
UInt64 FreeSpace;
UInt64 ClusterSize;
- UString Type;
+ // UString Type;
UString VolumeName;
UString FileSystemName;
+ UINT DriveType;
+
+ UString GetDeviceFileIoName() const;
};
class CFSDrives:
public IFolderFolder,
+ public IFolderOperations,
public IFolderGetSystemIconIndex,
public CMyUnknownImp
{
+ CObjectVector<CDriveInfo> _drives;
+ bool _volumeMode;
+
+ HRESULT BindToFolderSpec(const wchar_t *name, IFolderFolder **resultFolder);
+ UString GetExt(int index) const;
+ HRESULT GetLength(int index, UInt64 &length) const;
public:
- MY_UNKNOWN_IMP1(
- IFolderGetSystemIconIndex
- )
+ MY_UNKNOWN_IMP2(IFolderGetSystemIconIndex, IFolderOperations)
INTERFACE_FolderFolder(;)
+ INTERFACE_FolderOperations(;)
- STDMETHOD(GetSystemIconIndex)(UInt32 index, INT32 *iconIndex);
+ STDMETHOD(GetSystemIconIndex)(UInt32 index, Int32 *iconIndex);
-private:
- HRESULT BindToFolderSpec(const wchar_t *name, IFolderFolder **resultFolder);
- CObjectVector<CDriveInfo> _drives;
- bool _volumeMode;
-public:
- void Init() { _volumeMode = false;}
+ void Init(bool volMode = false)
+ {
+ _volumeMode = volMode;
+ }
};
#endif
diff --git a/CPP/7zip/UI/FileManager/FSFolder.cpp b/CPP/7zip/UI/FileManager/FSFolder.cpp
index 604c9b9c..5951fc09 100755
--- a/CPP/7zip/UI/FileManager/FSFolder.cpp
+++ b/CPP/7zip/UI/FileManager/FSFolder.cpp
@@ -2,22 +2,20 @@
#include "StdAfx.h"
-#include "FSFolder.h"
-
+#include "Common/ComTry.h"
#include "Common/StringConvert.h"
#include "Common/UTFConvert.h"
-#include "Common/ComTry.h"
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
#include "Windows/FileDir.h"
#include "Windows/FileIO.h"
+#include "Windows/PropVariant.h"
#include "../../PropID.h"
-#include "SysIconUtils.h"
#include "FSDrives.h"
+#include "FSFolder.h"
#include "NetFolder.h"
+#include "SysIconUtils.h"
namespace NWindows {
namespace NFile {
@@ -32,10 +30,9 @@ using namespace NFind;
namespace NFsFolder {
-static STATPROPSTG kProperties[] =
+static STATPROPSTG kProps[] =
{
{ NULL, kpidName, VT_BSTR},
- // { NULL, kpidIsDir, VT_BOOL},
{ NULL, kpidSize, VT_UI8},
{ NULL, kpidMTime, VT_FILETIME},
{ NULL, kpidCTime, VT_FILETIME},
@@ -152,7 +149,7 @@ void CFSFolder::AddRefs(CDirItem &dirItem)
STDMETHODIMP CFSFolder::LoadItems()
{
// OutputDebugString(TEXT("Start\n"));
- INT32 dummy;
+ Int32 dummy;
WasChanged(&dummy);
Clear();
RINOK(LoadSubItems(_root, _path));
@@ -394,24 +391,13 @@ STDMETHODIMP CFSFolder::BindToParentFolder(IFolderFolder **resultFolder)
STDMETHODIMP CFSFolder::GetNumberOfProperties(UInt32 *numProperties)
{
- *numProperties = sizeof(kProperties) / sizeof(kProperties[0]);
+ *numProperties = sizeof(kProps) / sizeof(kProps[0]);
if (!_flatMode)
(*numProperties)--;
return S_OK;
}
-STDMETHODIMP CFSFolder::GetPropertyInfo(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType)
-{
- if (index >= sizeof(kProperties) / sizeof(kProperties[0]))
- return E_INVALIDARG;
- const STATPROPSTG &prop = kProperties[index];
- *propID = prop.propid;
- *varType = prop.vt;
- *name = 0;
- return S_OK;
-}
-
+STDMETHODIMP CFSFolder::GetPropertyInfo IMP_IFolderFolder_GetProp(kProps)
STDMETHODIMP CFSFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
{
@@ -427,7 +413,7 @@ STDMETHODIMP CFSFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
COM_TRY_END
}
-STDMETHODIMP CFSFolder::WasChanged(INT32 *wasChanged)
+STDMETHODIMP CFSFolder::WasChanged(Int32 *wasChanged)
{
bool wasChangedMain = false;
for (;;)
@@ -640,7 +626,7 @@ STDMETHODIMP CFSFolder::SetProperty(UInt32 index, PROPID propID,
return S_OK;
}
-STDMETHODIMP CFSFolder::GetSystemIconIndex(UInt32 index, INT32 *iconIndex)
+STDMETHODIMP CFSFolder::GetSystemIconIndex(UInt32 index, Int32 *iconIndex)
{
if (index >= (UInt32)_refs.Size())
return E_INVALIDARG;
diff --git a/CPP/7zip/UI/FileManager/FSFolder.h b/CPP/7zip/UI/FileManager/FSFolder.h
index ca229055..95f40bb3 100755
--- a/CPP/7zip/UI/FileManager/FSFolder.h
+++ b/CPP/7zip/UI/FileManager/FSFolder.h
@@ -5,11 +5,10 @@
#include "Common/MyString.h"
#include "Common/MyCom.h"
+
#include "Windows/FileFind.h"
-#include "Windows/PropVariant.h"
#include "IFolder.h"
-
#include "TextPairs.h"
namespace NFsFolder {
@@ -65,13 +64,13 @@ public:
INTERFACE_FolderFolder(;)
INTERFACE_FolderOperations(;)
- STDMETHOD(WasChanged)(INT32 *wasChanged);
+ STDMETHOD(WasChanged)(Int32 *wasChanged);
STDMETHOD(Clone)(IFolderFolder **resultFolder);
STDMETHOD(GetItemFullSize)(UInt32 index, PROPVARIANT *value, IProgress *progress);
STDMETHOD(SetFlatMode)(Int32 flatMode);
- STDMETHOD(GetSystemIconIndex)(UInt32 index, INT32 *iconIndex);
+ STDMETHOD(GetSystemIconIndex)(UInt32 index, Int32 *iconIndex);
private:
UString _path;
diff --git a/CPP/7zip/UI/FileManager/FSFolderCopy.cpp b/CPP/7zip/UI/FileManager/FSFolderCopy.cpp
index b2d057df..9711616c 100755
--- a/CPP/7zip/UI/FileManager/FSFolderCopy.cpp
+++ b/CPP/7zip/UI/FileManager/FSFolderCopy.cpp
@@ -4,14 +4,15 @@
#include <Winbase.h>
-#include "FSFolder.h"
+#include "Common/StringConvert.h"
+
#include "Windows/FileDir.h"
#include "Windows/Error.h"
-#include "Common/StringConvert.h"
-
#include "../../Common/FilePathAutoRename.h"
+#include "FSFolder.h"
+
using namespace NWindows;
using namespace NFile;
using namespace NFind;
@@ -189,7 +190,7 @@ static HRESULT MyCopyFile(
return E_ABORT;
}
- INT32 writeAskResult;
+ Int32 writeAskResult;
CMyComBSTR destPathResult;
RINOK(callback->AskWrite(
srcPath,
@@ -340,7 +341,7 @@ HRESULT MyMoveFile(
return E_ABORT;
}
- INT32 writeAskResult;
+ Int32 writeAskResult;
CMyComBSTR destPathResult;
RINOK(callback->AskWrite(
srcPath,
@@ -510,5 +511,5 @@ STDMETHODIMP CFSFolder::CopyFrom(const wchar_t * /* fromFolderPath */,
*/
return E_NOTIMPL;
}
-
+
}
diff --git a/CPP/7zip/UI/FileManager/FileFolderPluginOpen.cpp b/CPP/7zip/UI/FileManager/FileFolderPluginOpen.cpp
index 3cd79da0..992fbd8c 100755
--- a/CPP/7zip/UI/FileManager/FileFolderPluginOpen.cpp
+++ b/CPP/7zip/UI/FileManager/FileFolderPluginOpen.cpp
@@ -4,21 +4,15 @@
#include "resource.h"
-#include "Common/StringConvert.h"
-#include "Windows/Defs.h"
-#include "Windows/FileDir.h"
-#include "Windows/FileName.h"
-#include "Windows/DLL.h"
#include "Windows/Thread.h"
-#include "IFolder.h"
-#include "RegistryAssociations.h"
-#include "RegistryPlugins.h"
+#include "../Agent/Agent.h"
+#include "LangUtils.h"
#include "OpenCallback.h"
#include "PluginLoader.h"
-#include "LangUtils.h"
-#include "../Agent/Agent.h"
+#include "RegistryAssociations.h"
+#include "RegistryPlugins.h"
using namespace NWindows;
using namespace NRegistryAssociations;
@@ -26,6 +20,7 @@ using namespace NRegistryAssociations;
struct CThreadArchiveOpen
{
UString Path;
+ CMyComPtr<IInStream> InStream;
CMyComPtr<IFolderManager> FolderManager;
CMyComPtr<IProgress> OpenCallback;
COpenArchiveCallback *OpenCallbackSpec;
@@ -36,7 +31,7 @@ struct CThreadArchiveOpen
void Process()
{
OpenCallbackSpec->ProgressDialog.WaitCreating();
- Result = FolderManager->OpenFolderFile(Path, &Folder, OpenCallback);
+ Result = FolderManager->OpenFolderFile(InStream, Path, &Folder, OpenCallback);
OpenCallbackSpec->ProgressDialog.MyClose();
}
@@ -57,6 +52,7 @@ static int FindPlugin(const CObjectVector<CPluginInfo> &plugins,
}
HRESULT OpenFileFolderPlugin(
+ IInStream *inStream,
const UString &path,
HMODULE *module,
IFolderFolder **resultFolder,
@@ -66,13 +62,7 @@ HRESULT OpenFileFolderPlugin(
CObjectVector<CPluginInfo> plugins;
ReadFileFolderPluginInfoList(plugins);
- UString extension;
- UString name, pureName, dot;
-
- if(!NFile::NDirectory::GetOnlyName(path, name))
- return E_FAIL;
- NFile::NName::SplitNameToPureNameAndExtension(name, pureName, dot, extension);
-
+ UString extension, name, pureName, dot;
int slashPos = path.ReverseFind(WCHAR_PATH_SEPARATOR);
UString dirPrefix;
@@ -85,6 +75,8 @@ HRESULT OpenFileFolderPlugin(
else
fileName = path;
+ NFile::NName::SplitNameToPureNameAndExtension(fileName, pureName, dot, extension);
+
if (!extension.IsEmpty())
{
CExtInfo extInfo;
@@ -122,8 +114,13 @@ HRESULT OpenFileFolderPlugin(
t.OpenCallbackSpec->PasswordIsDefined = encrypted;
t.OpenCallbackSpec->Password = password;
t.OpenCallbackSpec->ParentWindow = parentWindow;
- t.OpenCallbackSpec->LoadFileInfo(dirPrefix, fileName);
+ if (inStream)
+ t.OpenCallbackSpec->SetSubArchiveName(fileName);
+ else
+ t.OpenCallbackSpec->LoadFileInfo(dirPrefix, fileName);
+
+ t.InStream = inStream;
t.Path = path;
UString progressTitle = LangString(IDS_OPENNING, 0x03020283);
diff --git a/CPP/7zip/UI/FileManager/FileFolderPluginOpen.h b/CPP/7zip/UI/FileManager/FileFolderPluginOpen.h
index 9e5c66c7..692417ba 100755
--- a/CPP/7zip/UI/FileManager/FileFolderPluginOpen.h
+++ b/CPP/7zip/UI/FileManager/FileFolderPluginOpen.h
@@ -1,9 +1,9 @@
// FileFolderPluginOpen.h
-#ifndef __FILEFOLDERPLUGINOPEN_H
-#define __FILEFOLDERPLUGINOPEN_H
+#ifndef __FILE_FOLDER_PLUGIN_OPEN_H
+#define __FILE_FOLDER_PLUGIN_OPEN_H
-HRESULT OpenFileFolderPlugin(const UString &path,
+HRESULT OpenFileFolderPlugin(IInStream *inStream, const UString &path,
HMODULE *module, IFolderFolder **resultFolder, HWND parentWindow, bool &encrypted, UString &password);
#endif
diff --git a/CPP/7zip/UI/FileManager/IFolder.h b/CPP/7zip/UI/FileManager/IFolder.h
index 6709cd1e..b301f513 100755
--- a/CPP/7zip/UI/FileManager/IFolder.h
+++ b/CPP/7zip/UI/FileManager/IFolder.h
@@ -4,6 +4,7 @@
#define __IFOLDER_H
#include "../../IProgress.h"
+#include "../../IStream.h"
#define FOLDER_INTERFACE_SUB(i, b, x) DECL_INTERFACE_SUB(i, b, 8, x)
#define FOLDER_INTERFACE(i, x) FOLDER_INTERFACE_SUB(i, IUnknown, x)
@@ -106,7 +107,7 @@ FOLDER_INTERFACE(IFolderSetFlatMode, 0x0A)
STDMETHOD(GetNumberOfFolderProperties)(UInt32 *numProperties) x; \
STDMETHOD(GetFolderPropertyInfo)(UInt32 index, BSTR *name, PROPID *propID, VARTYPE *varType) x; \
-FOLDER_INTERFACE(IFolderProperties, 0x0B)
+FOLDER_INTERFACE(IFolderProperties, 0x0E)
{
INTERFACE_FolderProperties(PURE)
};
@@ -129,17 +130,28 @@ FOLDER_INTERFACE(IGetFolderArchiveProperties, 0x0D)
#define FOLDER_MANAGER_INTERFACE(i, x) DECL_INTERFACE(i, 9, x)
#define INTERFACE_IFolderManager(x) \
- STDMETHOD(OpenFolderFile)(const wchar_t *filePath, IFolderFolder **resultFolder, IProgress *progress) x; \
+ STDMETHOD(OpenFolderFile)(IInStream *inStream, const wchar_t *filePath, IFolderFolder **resultFolder, IProgress *progress) x; \
STDMETHOD(GetExtensions)(BSTR *extensions) x; \
STDMETHOD(GetIconPath)(const wchar_t *ext, BSTR *iconPath, Int32 *iconIndex) x; \
// STDMETHOD(GetTypes)(BSTR *types) PURE;
// STDMETHOD(CreateFolderFile)(const wchar_t *type, const wchar_t *filePath, IProgress *progress) PURE;
-FOLDER_MANAGER_INTERFACE(IFolderManager, 0x03)
+FOLDER_MANAGER_INTERFACE(IFolderManager, 0x04)
{
INTERFACE_IFolderManager(PURE);
};
+#define IMP_IFolderFolder_GetProp(k) \
+ (UInt32 index, BSTR *name, PROPID *propID, VARTYPE *varType) \
+ { if(index >= sizeof(k) / sizeof(k[0])) return E_INVALIDARG; \
+ const STATPROPSTG &srcItem = k[index]; \
+ *propID = srcItem.propid; *varType = srcItem.vt; *name = 0; return S_OK; } \
+
+#define IMP_IFolderFolder_Props(c) \
+ STDMETHODIMP c::GetNumberOfProperties(UInt32 *numProperties) \
+ { *numProperties = sizeof(kProps) / sizeof(kProps[0]); return S_OK; } \
+ STDMETHODIMP c::GetPropertyInfo IMP_IFolderFolder_GetProp(kProps)
+
#endif
diff --git a/CPP/7zip/UI/FileManager/LangPage.rc b/CPP/7zip/UI/FileManager/LangPage.rc
index 0e06406c..bd4d83d8 100755
--- a/CPP/7zip/UI/FileManager/LangPage.rc
+++ b/CPP/7zip/UI/FileManager/LangPage.rc
@@ -1,8 +1,8 @@
#include "LangPageRes.h"
#include "../../GuiCommon.rc"
-#define xSize2 238
-#define ySize2 204
+#define xSize2 196
+#define ySize2 140
#define xSize (xSize2 + marg + marg)
#define ySize (ySize2 + marg + marg)
diff --git a/CPP/7zip/UI/FileManager/LangUtils.cpp b/CPP/7zip/UI/FileManager/LangUtils.cpp
index 0591c73c..52f85348 100755
--- a/CPP/7zip/UI/FileManager/LangUtils.cpp
+++ b/CPP/7zip/UI/FileManager/LangUtils.cpp
@@ -104,7 +104,8 @@ void LoadLangs(CObjectVector<CLangEx> &langs)
CLangEx lang;
UString filePath = folderPath + fileInfo.Name;
const int kExtSize = 4;
- if (fileInfo.Name.Right(kExtSize) != L".txt")
+ const UString ext = fileInfo.Name.Right(kExtSize);
+ if (ext.CompareNoCase(L".txt") != 0)
continue;
lang.ShortName = fileInfo.Name.Left(fileInfo.Name.Length() - kExtSize);
if (lang.Lang.Open(filePath))
diff --git a/CPP/7zip/UI/FileManager/ListViewDialog.cpp b/CPP/7zip/UI/FileManager/ListViewDialog.cpp
index 7a78fcde..e8001cf6 100755
--- a/CPP/7zip/UI/FileManager/ListViewDialog.cpp
+++ b/CPP/7zip/UI/FileManager/ListViewDialog.cpp
@@ -43,6 +43,9 @@ bool CListViewDialog::OnNotify(UINT /* controlID */, LPNMHDR header)
return false;
switch(header->code)
{
+ case NM_DBLCLK:
+ OnOK();
+ return true;
case LVN_KEYDOWN:
{
LPNMLVKEYDOWN keyDownInfo = LPNMLVKEYDOWN(header);
diff --git a/CPP/7zip/UI/FileManager/MyLoadMenu.cpp b/CPP/7zip/UI/FileManager/MyLoadMenu.cpp
index c6f57f9e..f98325a0 100755
--- a/CPP/7zip/UI/FileManager/MyLoadMenu.cpp
+++ b/CPP/7zip/UI/FileManager/MyLoadMenu.cpp
@@ -1,23 +1,20 @@
-// MyLoadMenu
+// MyLoadMenu.cpp
#include "StdAfx.h"
-#include "Common/StringConvert.h"
-
#include "Windows/Menu.h"
-#include "Windows/Error.h"
-#include "Windows/Clipboard.h"
#include "../../PropID.h"
-#include "resource.h"
-#include "App.h"
-#include "AboutDialog.h"
#include "../Common/CompressCall.h"
+#include "AboutDialog.h"
+#include "App.h"
#include "HelpUtils.h"
#include "LangUtils.h"
-#include "PluginInterface.h"
+#include "RegistryUtils.h"
+
+#include "resource.h"
static const UINT kOpenBookmarkMenuID = 730;
static const UINT kSetBookmarkMenuID = 740;
@@ -428,6 +425,9 @@ void LoadFileMenu(HMENU hMenu, int startPos, bool programMenu,
CMenu destMenu;
destMenu.Attach(hMenu);
+
+ UString diffPath;
+ ReadRegDiff(diffPath);
for (int i = 0; i < g_FileMenu.GetItemCount(); i++)
{
@@ -440,6 +440,10 @@ void LoadFileMenu(HMENU hMenu, int startPos, bool programMenu,
if (!programMenu)
if (item.wID == IDCLOSE)
continue;
+
+ if (item.wID == IDM_FILE_DIFF && diffPath.IsEmpty())
+ continue;
+
bool isOneFsFile = (isFsFolder && numItems == 1 && allAreFiles);
if ((item.wID == IDM_FILE_SPLIT || item.wID == IDM_FILE_COMBINE) && !isOneFsFile)
item.fState |= MFS_DISABLED;
@@ -522,6 +526,9 @@ bool ExecuteFileCommand(int id)
case IDM_FILE_CRC:
g_App.CalculateCrc();
break;
+ case IDM_FILE_DIFF:
+ g_App.DiffFiles();
+ break;
case IDM_FILE_SPLIT:
g_App.Split();
break;
diff --git a/CPP/7zip/UI/FileManager/NetFolder.cpp b/CPP/7zip/UI/FileManager/NetFolder.cpp
index d3298c62..e1fa1965 100755
--- a/CPP/7zip/UI/FileManager/NetFolder.cpp
+++ b/CPP/7zip/UI/FileManager/NetFolder.cpp
@@ -2,21 +2,18 @@
#include "StdAfx.h"
-#include "NetFolder.h"
+#include "Windows/PropVariant.h"
-#include "Common/StringConvert.h"
#include "../../PropID.h"
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
-#include "Windows/FileFind.h"
-#include "SysIconUtils.h"
#include "FSFolder.h"
+#include "NetFolder.h"
+#include "SysIconUtils.h"
using namespace NWindows;
using namespace NNet;
-static const STATPROPSTG kProperties[] =
+static const STATPROPSTG kProps[] =
{
{ NULL, kpidName, VT_BSTR},
{ NULL, kpidLocalName, VT_BSTR},
@@ -232,23 +229,7 @@ STDMETHODIMP CNetFolder::BindToParentFolder(IFolderFolder **resultFolder)
return S_OK;
}
-STDMETHODIMP CNetFolder::GetNumberOfProperties(UInt32 *numProperties)
-{
- *numProperties = sizeof(kProperties) / sizeof(kProperties[0]);
- return S_OK;
-}
-
-STDMETHODIMP CNetFolder::GetPropertyInfo(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType)
-{
- if (index >= sizeof(kProperties) / sizeof(kProperties[0]))
- return E_INVALIDARG;
- const STATPROPSTG &prop = kProperties[index];
- *propID = prop.propid;
- *varType = prop.vt;
- *name = 0;
- return S_OK;
-}
+IMP_IFolderFolder_Props(CNetFolder)
STDMETHODIMP CNetFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
{
@@ -262,7 +243,7 @@ STDMETHODIMP CNetFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
return S_OK;
}
-STDMETHODIMP CNetFolder::GetSystemIconIndex(UInt32 index, INT32 *iconIndex)
+STDMETHODIMP CNetFolder::GetSystemIconIndex(UInt32 index, Int32 *iconIndex)
{
if (index >= (UInt32)_items.Size())
return E_INVALIDARG;
diff --git a/CPP/7zip/UI/FileManager/NetFolder.h b/CPP/7zip/UI/FileManager/NetFolder.h
index 92471ec6..9962845c 100755
--- a/CPP/7zip/UI/FileManager/NetFolder.h
+++ b/CPP/7zip/UI/FileManager/NetFolder.h
@@ -1,12 +1,10 @@
// NetFolder.h
-#ifndef __NETFOLDER_H
-#define __NETFOLDER_H
+#ifndef __NET_FOLDER_H
+#define __NET_FOLDER_H
-#include "Common/MyString.h"
-#include "Common/Buffer.h"
#include "Common/MyCom.h"
-#include "Windows/PropVariant.h"
+
#include "Windows/Net.h"
#include "IFolder.h"
@@ -21,16 +19,6 @@ class CNetFolder:
public IFolderGetSystemIconIndex,
public CMyUnknownImp
{
-public:
- MY_UNKNOWN_IMP1(
- IFolderGetSystemIconIndex
- )
-
- INTERFACE_FolderFolder(;)
-
- STDMETHOD(GetSystemIconIndex)(UInt32 index, INT32 *iconIndex);
-
-private:
NWindows::NNet::CResourceW _netResource;
NWindows::NNet::CResourceW *_netResourcePointer;
@@ -38,12 +26,15 @@ private:
CMyComPtr<IFolderFolder> _parentFolder;
UString _path;
-
public:
+ MY_UNKNOWN_IMP1(IFolderGetSystemIconIndex)
+ INTERFACE_FolderFolder(;)
+ STDMETHOD(GetSystemIconIndex)(UInt32 index, Int32 *iconIndex);
+
+ CNetFolder(): _netResourcePointer(0) {}
void Init(const UString &path);
void Init(const NWindows::NNet::CResourceW *netResource,
IFolderFolder *parentFolder, const UString &path);
- CNetFolder(): _netResourcePointer(0) {}
};
#endif
diff --git a/CPP/7zip/UI/FileManager/OpenCallback.cpp b/CPP/7zip/UI/FileManager/OpenCallback.cpp
index 9c71a291..a275f89b 100755
--- a/CPP/7zip/UI/FileManager/OpenCallback.cpp
+++ b/CPP/7zip/UI/FileManager/OpenCallback.cpp
@@ -2,50 +2,48 @@
#include "StdAfx.h"
-#include "OpenCallback.h"
-
#include "Common/StringConvert.h"
+
#include "Windows/PropVariant.h"
#include "../../Common/FileStreams.h"
+#include "OpenCallback.h"
#include "PasswordDialog.h"
+using namespace NWindows;
+
STDMETHODIMP COpenArchiveCallback::SetTotal(const UInt64 *numFiles, const UInt64 *numBytes)
{
+ RINOK(ProgressDialog.ProgressSynch.ProcessStopAndPause());
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
- _numFilesTotalDefined = (numFiles != NULL);
- _numBytesTotalDefined = (numBytes != NULL);
- if (_numFilesTotalDefined)
+ NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ if (numFiles != NULL)
{
ProgressDialog.ProgressSynch.SetNumFilesTotal(*numFiles);
- ProgressDialog.ProgressSynch.SetProgress(*numFiles, 0);
+ ProgressDialog.ProgressSynch.SetBytesProgressMode(false);
}
- else if (_numBytesTotalDefined)
- ProgressDialog.ProgressSynch.SetProgress(*numBytes, 0);
+ if (numBytes != NULL)
+ ProgressDialog.ProgressSynch.SetNumBytesTotal(*numBytes);
}
return S_OK;
}
STDMETHODIMP COpenArchiveCallback::SetCompleted(const UInt64 *numFiles, const UInt64 *numBytes)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
RINOK(ProgressDialog.ProgressSynch.ProcessStopAndPause());
+ NSynchronization::CCriticalSectionLock lock(_criticalSection);
if (numFiles != NULL)
- {
ProgressDialog.ProgressSynch.SetNumFilesCur(*numFiles);
- if (_numFilesTotalDefined)
- ProgressDialog.ProgressSynch.SetPos(*numFiles);
- }
- if (numBytes != NULL && _numBytesTotalDefined)
+ if (numBytes != NULL)
ProgressDialog.ProgressSynch.SetPos(*numBytes);
return S_OK;
}
STDMETHODIMP COpenArchiveCallback::SetTotal(const UInt64 total)
{
- ProgressDialog.ProgressSynch.SetProgress(total, 0);
+ RINOK(ProgressDialog.ProgressSynch.ProcessStopAndPause());
+ ProgressDialog.ProgressSynch.SetNumBytesTotal(total);
return S_OK;
}
@@ -59,7 +57,7 @@ STDMETHODIMP COpenArchiveCallback::SetCompleted(const UInt64 *completed)
STDMETHODIMP COpenArchiveCallback::GetProperty(PROPID propID, PROPVARIANT *value)
{
- NWindows::NCOM::CPropVariant prop;
+ NCOM::CPropVariant prop;
if (_subArchiveMode)
{
switch(propID)
@@ -91,10 +89,10 @@ STDMETHODIMP COpenArchiveCallback::GetStream(const wchar_t *name,
if (_subArchiveMode)
return S_FALSE;
- NWindows::NFile::NFind::CFileInfoW fileInfo;
+ NFile::NFind::CFileInfoW fileInfo;
UString fullPath = _folderPrefix + name;
- if (!NWindows::NFile::NFind::FindFile(fullPath, fileInfo))
+ if (!fileInfo.Find(fullPath))
return S_FALSE;
_fileInfo = fileInfo;
if (_fileInfo.IsDir())
diff --git a/CPP/7zip/UI/FileManager/OpenCallback.h b/CPP/7zip/UI/FileManager/OpenCallback.h
index 168f171b..5f0fbefc 100755
--- a/CPP/7zip/UI/FileManager/OpenCallback.h
+++ b/CPP/7zip/UI/FileManager/OpenCallback.h
@@ -3,15 +3,15 @@
#ifndef __OPENCALLBACK_H
#define __OPENCALLBACK_H
-#include "Common/MyString.h"
#include "Common/MyCom.h"
+#include "Common/MyString.h"
+
#include "Windows/FileFind.h"
#include "../../IPassword.h"
#include "../../Archive/IArchive.h"
-
#ifdef _SFX
#include "ProgressDialog.h"
#else
@@ -29,21 +29,15 @@ class COpenArchiveCallback:
{
UString _folderPrefix;
NWindows::NFile::NFind::CFileInfoW _fileInfo;
-
- bool _numFilesTotalDefined;
- bool _numBytesTotalDefined;
NWindows::NSynchronization::CCriticalSection _criticalSection;
+ bool _subArchiveMode;
+ UString _subArchiveName;
public:
bool PasswordIsDefined;
- UString Password;
bool PasswordWasAsked;
+ UString Password;
HWND ParentWindow;
-
- bool _subArchiveMode;
- UString _subArchiveName;
-
-public:
CProgressDialog ProgressDialog;
MY_UNKNOWN_IMP5(
@@ -70,9 +64,6 @@ public:
COpenArchiveCallback():
ParentWindow(0)
{
- _numFilesTotalDefined = false;
- _numBytesTotalDefined = false;
-
_subArchiveMode = false;
PasswordIsDefined = false;
PasswordWasAsked = false;
@@ -87,7 +78,7 @@ public:
void LoadFileInfo(const UString &folderPrefix, const UString &fileName)
{
_folderPrefix = folderPrefix;
- if (!NWindows::NFile::NFind::FindFile(_folderPrefix + fileName, _fileInfo))
+ if (!_fileInfo.Find(_folderPrefix + fileName))
throw 1;
}
void ShowMessage(const UInt64 *completed);
@@ -96,7 +87,6 @@ public:
{
return ProgressDialog.Create(title, ParentWindow);
}
-
};
#endif
diff --git a/CPP/7zip/UI/FileManager/Panel.cpp b/CPP/7zip/UI/FileManager/Panel.cpp
index 40192c5f..9255b117 100755
--- a/CPP/7zip/UI/FileManager/Panel.cpp
+++ b/CPP/7zip/UI/FileManager/Panel.cpp
@@ -5,28 +5,30 @@
#include <Windowsx.h>
#include "Common/Defs.h"
-#include "Common/StringConvert.h"
#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
+
#include "Windows/Error.h"
#include "Windows/PropVariant.h"
#include "Windows/Thread.h"
#include "../../PropID.h"
-#include "Panel.h"
-#include "RootFolder.h"
-#include "FSFolder.h"
-#include "FormatUtils.h"
-#include "App.h"
-#include "ExtractCallback.h"
-
#include "resource.h"
-#include "..\GUI\ExtractRes.h"
+#include "../GUI/ExtractRes.h"
+
+#include "../Common/ArchiveName.h"
+#include "../Common/CompressCall.h"
#include "../Agent/IFolderArchive.h"
-#include "../Common/CompressCall.h"
-#include "../Common/ArchiveName.h"
+#include "App.h"
+#include "ExtractCallback.h"
+#include "FSFolder.h"
+#include "FormatUtils.h"
+#include "Panel.h"
+#include "RootFolder.h"
+
using namespace NWindows;
using namespace NControl;
@@ -707,7 +709,7 @@ bool CPanel::IsFSDrivesFolder() const
UString CPanel::GetFsPath() const
{
- if (IsFSDrivesFolder())
+ if (IsFSDrivesFolder() && !IsDeviceDrivesPrefix())
return UString();
return _currentFolderPrefix;
}
@@ -773,7 +775,7 @@ void CPanel::AddToArchive()
{
CRecordVector<UInt32> indices;
GetOperatedItemIndices(indices);
- if (!IsFSFolder())
+ if (!IsFsOrDrivesFolder())
{
MessageBoxErrorLang(IDS_OPERATION_IS_NOT_SUPPORTED, 0x03020208);
return;
@@ -784,14 +786,25 @@ void CPanel::AddToArchive()
return;
}
UStringVector names;
+
+ UString curPrefix = _currentFolderPrefix;
+ UString destCurDirPrefix = _currentFolderPrefix;
+ if (IsFSDrivesFolder())
+ {
+ destCurDirPrefix = L"C:\\";
+ if (!IsDeviceDrivesPrefix())
+ curPrefix.Empty();
+ }
+
for (int i = 0; i < indices.Size(); i++)
{
int index = indices[i];
- names.Add(_currentFolderPrefix + GetItemRelPath(index));
+ names.Add(curPrefix + GetItemRelPath(index));
}
const UString archiveName = CreateArchiveName(
names.Front(), (names.Size() > 1), false);
- HRESULT res = CompressFiles(_currentFolderPrefix, archiveName, L"", names, false, true, false);
+
+ HRESULT res = CompressFiles(destCurDirPrefix, archiveName, L"", names, false, true, false);
if (res != S_OK)
{
if (_currentFolderPrefix.Length() >= MAX_PATH)
@@ -823,7 +836,7 @@ void CPanel::GetFilePaths(const CRecordVector<UInt32> &indices, UStringVector &p
paths.Clear();
break;
}
- paths.Add(_currentFolderPrefix + GetItemRelPath(index));
+ paths.Add(GetItemFullPath(index));
}
if (paths.Size() == 0)
{
diff --git a/CPP/7zip/UI/FileManager/Panel.h b/CPP/7zip/UI/FileManager/Panel.h
index 4ba36a71..ed157634 100755
--- a/CPP/7zip/UI/FileManager/Panel.h
+++ b/CPP/7zip/UI/FileManager/Panel.h
@@ -6,25 +6,24 @@
#include "Common/MyCom.h"
#include "Windows/DLL.h"
-#include "Windows/FileFind.h"
#include "Windows/FileDir.h"
-#include "Windows/Synchronization.h"
+#include "Windows/FileFind.h"
#include "Windows/Handle.h"
+#include "Windows/Synchronization.h"
-#include "Windows/Control/ToolBar.h"
-#include "Windows/Control/ReBar.h"
+#include "Windows/Control/ComboBox.h"
+#include "Windows/Control/Edit.h"
#include "Windows/Control/ListView.h"
+#include "Windows/Control/ReBar.h"
#include "Windows/Control/Static.h"
-#include "Windows/Control/Edit.h"
-#include "Windows/Control/ComboBox.h"
-#include "Windows/Control/Window2.h"
#include "Windows/Control/StatusBar.h"
+#include "Windows/Control/ToolBar.h"
+#include "Windows/Control/Window2.h"
-#include "SysIconUtils.h"
-#include "IFolder.h"
-#include "ViewSettings.h"
#include "AppState.h"
+#include "IFolder.h"
#include "MyCom2.h"
+#include "SysIconUtils.h"
const int kParentFolderID = 100;
const int kPluginMenuStartID = 1000;
@@ -81,10 +80,21 @@ struct CTempFileInfo
UString FolderPath;
UString FilePath;
NWindows::NFile::NFind::CFileInfoW FileInfo;
- void DeleteDirAndFile()
+ bool NeedDelete;
+
+ CTempFileInfo(): NeedDelete(false) {}
+ void DeleteDirAndFile() const
{
- NWindows::NFile::NDirectory::DeleteFileAlways(FilePath);
- NWindows::NFile::NDirectory::MyRemoveDirectory(FolderPath);
+ if (NeedDelete)
+ {
+ NWindows::NFile::NDirectory::DeleteFileAlways(FilePath);
+ NWindows::NFile::NDirectory::MyRemoveDirectory(FolderPath);
+ }
+ }
+ bool WasChanged(const NWindows::NFile::NFind::CFileInfoW &newFileInfo) const
+ {
+ return newFileInfo.Size != FileInfo.Size ||
+ CompareFileTime(&newFileInfo.MTime, &FileInfo.MTime) != 0;
}
};
@@ -94,9 +104,16 @@ struct CFolderLink: public CTempFileInfo
CMyComPtr<IFolderFolder> ParentFolder;
bool UsePassword;
UString Password;
+ bool IsVirtual;
UString VirtualPath;
- CFolderLink(): UsePassword(false) {}
+ CFolderLink(): UsePassword(false), IsVirtual(false) {}
+
+ bool WasChanged(const NWindows::NFile::NFind::CFileInfoW &newFileInfo) const
+ {
+ return IsVirtual || CTempFileInfo::WasChanged(newFileInfo);
+ }
+
};
enum MyMessages
@@ -294,6 +311,7 @@ public:
UString GetItemName(int itemIndex) const;
UString GetItemPrefix(int itemIndex) const;
UString GetItemRelPath(int itemIndex) const;
+ UString GetItemFullPath(int itemIndex) const;
bool IsItemFolder(int itemIndex) const;
UInt64 GetItemSize(int itemIndex) const;
@@ -419,6 +437,9 @@ public:
bool IsRootFolder() const;
bool IsFSFolder() const;
bool IsFSDrivesFolder() const;
+ bool IsFsOrDrivesFolder() const { return IsFSFolder() || IsFSDrivesFolder(); }
+ bool IsDeviceDrivesPrefix() const { return _currentFolderPrefix == L"\\\\.\\"; }
+ bool IsFsOrPureDrivesFolder() const { return IsFSFolder() || (IsFSDrivesFolder() && !IsDeviceDrivesPrefix()); }
UString GetFsPath() const;
UString GetDriveOrNetworkPrefix() const;
@@ -482,12 +503,11 @@ public:
void OpenFolder(int index);
HRESULT OpenParentArchiveFolder();
- HRESULT OpenItemAsArchive(const UString &name,
- const UString &folderPath,
- const UString &filePath,
+ HRESULT OpenItemAsArchive(IInStream *inStream,
+ const CTempFileInfo &tempFileInfo,
const UString &virtualFilePath,
bool &encrypted);
- HRESULT OpenItemAsArchive(const UString &name);
+ HRESULT OpenItemAsArchive(const UString &name, bool &encrypted);
HRESULT OpenItemAsArchive(int index);
void OpenItemInArchive(int index, bool tryInternal, bool tryExternal,
bool editMode);
diff --git a/CPP/7zip/UI/FileManager/PanelCrc.cpp b/CPP/7zip/UI/FileManager/PanelCrc.cpp
index 61a84050..aaa645cf 100755
--- a/CPP/7zip/UI/FileManager/PanelCrc.cpp
+++ b/CPP/7zip/UI/FileManager/PanelCrc.cpp
@@ -2,15 +2,11 @@
#include "StdAfx.h"
-extern "C"
-{
- #include "../../../../C/Alloc.h"
- #include "../../../../C/7zCrc.h"
- #include "../../../../C/Sha256.h"
-}
+#include "../../../../C/7zCrc.h"
+#include "../../../../C/Alloc.h"
+#include "../../../../C/Sha256.h"
#include "Common/IntToString.h"
-#include "Common/StringConvert.h"
#include "Windows/Error.h"
#include "Windows/FileFind.h"
@@ -25,6 +21,8 @@ extern "C"
#include "FormatUtils.h"
#include "LangUtils.h"
+#include "../Common/PropIDUtils.h"
+
#include "resource.h"
using namespace NWindows;
@@ -69,7 +67,18 @@ bool CDirEnumerator::GetNextFile(NFind::CFileInfoW &fileInfo, bool &filled, UStr
resPath.Empty();
if (pos >= 0)
resPath = path.Left(pos + 1);
- if (!NFind::FindFile(BasePrefix + path, fileInfo))
+
+ #ifdef _WIN32
+ // it's for "c:" paths/
+ if (BasePrefix.IsEmpty() && path.Length() == 2 && path[1] == ':')
+ {
+ fileInfo.Name = path;
+ fileInfo.Attrib = FILE_ATTRIBUTE_DIRECTORY;
+ fileInfo.Size = 0;
+ }
+ else
+ #endif
+ if (!fileInfo.Find(BasePrefix + path))
{
errorCode = ::GetLastError();
resPath = path;
@@ -285,21 +294,11 @@ static void ConvertByteToHex(unsigned value, wchar_t *s)
}
}
-static void ConvertUInt32ToHex(UInt32 value, wchar_t *s)
-{
- for (int i = 6; i >= 0; i -= 2)
- {
- ConvertByteToHex(value & 0xFF, s + i);
- value >>= 8;
- }
- s[8] = L'\0';
-}
-
void CApp::CalculateCrc()
{
int srcPanelIndex = GetFocusedPanelIndex();
CPanel &srcPanel = Panels[srcPanelIndex];
- if (!srcPanel.IsFSFolder())
+ if (!srcPanel.IsFsOrDrivesFolder())
{
srcPanel.MessageBoxErrorLang(IDS_OPERATION_IS_NOT_SUPPORTED, 0x03020208);
return;
@@ -312,7 +311,7 @@ void CApp::CalculateCrc()
CThreadCrc combiner;
for (int i = 0; i < indices.Size(); i++)
combiner.DirEnumerator.FileNames.Add(srcPanel.GetItemRelPath(indices[i]));
- combiner.DirEnumerator.BasePrefix = srcPanel._currentFolderPrefix;
+ combiner.DirEnumerator.BasePrefix = srcPanel.GetFsPath();
combiner.DirEnumerator.FlatMode = GetFlatMode();
{
diff --git a/CPP/7zip/UI/FileManager/PanelDrag.cpp b/CPP/7zip/UI/FileManager/PanelDrag.cpp
index 6cae36fe..6d1c9a29 100755
--- a/CPP/7zip/UI/FileManager/PanelDrag.cpp
+++ b/CPP/7zip/UI/FileManager/PanelDrag.cpp
@@ -459,7 +459,7 @@ void CDropTarget::PositionCursor(POINTL ptl)
return;
*/
- if (!m_Panel->IsFSFolder() && !m_Panel->IsFSDrivesFolder())
+ if (!m_Panel->IsFsOrPureDrivesFolder())
return;
if (WindowFromPoint(pt) != (HWND)m_Panel->_listView)
diff --git a/CPP/7zip/UI/FileManager/PanelFolderChange.cpp b/CPP/7zip/UI/FileManager/PanelFolderChange.cpp
index 01fec329..e6336f31 100755
--- a/CPP/7zip/UI/FileManager/PanelFolderChange.cpp
+++ b/CPP/7zip/UI/FileManager/PanelFolderChange.cpp
@@ -4,16 +4,18 @@
#include "Common/StringConvert.h"
#include "Common/Wildcard.h"
-#include "Windows/FileDir.h"
+
+#include "Windows/PropVariant.h"
#include "../../PropID.h"
-#include "Panel.h"
+#include "FSDrives.h"
+#include "LangUtils.h"
#include "ListViewDialog.h"
+#include "Panel.h"
#include "RootFolder.h"
#include "ViewSettings.h"
-#include "FSDrives.h"
-#include "LangUtils.h"
+
#include "resource.h"
using namespace NWindows;
@@ -71,7 +73,7 @@ HRESULT CPanel::BindToPath(const UString &fullPath, bool &archiveIsOpened, bool
UStringVector reducedParts;
while (!sysPath.IsEmpty())
{
- if (FindFile(sysPath, fileInfo))
+ if (fileInfo.Find(sysPath))
break;
int pos = sysPath.ReverseFind(WCHAR_PATH_SEPARATOR);
if (pos < 0)
@@ -108,11 +110,7 @@ HRESULT CPanel::BindToPath(const UString &fullPath, bool &archiveIsOpened, bool
UString fileName;
if (NDirectory::GetOnlyName(sysPath, fileName))
{
- HRESULT res =
- OpenItemAsArchive(fileName, _currentFolderPrefix,
- _currentFolderPrefix + fileName,
- _currentFolderPrefix + fileName,
- encrypted);
+ HRESULT res = OpenItemAsArchive(fileName, encrypted);
if (res != S_FALSE)
{
RINOK(res);
@@ -210,7 +208,7 @@ void CPanel::LoadFullPathAndShow()
CFileInfoW info;
DWORD attrib = FILE_ATTRIBUTE_DIRECTORY;
- if (NFile::NFind::FindFile(path, info))
+ if (info.Find(path))
attrib = info.Attrib;
item.iImage = GetRealIconIndex(path, attrib);
@@ -343,7 +341,7 @@ bool CPanel::OnComboBoxCommand(UINT code, LPARAM /* param */, LRESULT &result)
curName += WCHAR_PATH_SEPARATOR;
CFileInfoW info;
DWORD attrib = FILE_ATTRIBUTE_DIRECTORY;
- if (NFile::NFind::FindFile(sumPass, info))
+ if (info.Find(sumPass))
attrib = info.Attrib;
sumPass += WCHAR_PATH_SEPARATOR;
AddComboBoxItem(name, GetRealIconIndex(curName, attrib), i, false);
@@ -498,7 +496,7 @@ void CPanel::OpenParentFolder()
_folder = link.ParentFolder;
_library.Attach(link.Library.Detach());
focucedName = link.ItemName;
- if (_parentFolders.Size () > 1)
+ if (_parentFolders.Size() > 1)
OpenParentArchiveFolder();
_parentFolders.DeleteBack();
if (_parentFolders.IsEmpty())
@@ -526,7 +524,7 @@ void CPanel::CloseOpenFolders()
_library.Free();
_folder = _parentFolders.Back().ParentFolder;
_library.Attach(_parentFolders.Back().Library.Detach());
- if (_parentFolders.Size () > 1)
+ if (_parentFolders.Size() > 1)
OpenParentArchiveFolder();
_parentFolders.DeleteBack();
}
diff --git a/CPP/7zip/UI/FileManager/PanelItemOpen.cpp b/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
index c40b0d18..2aab2aae 100755
--- a/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
+++ b/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
@@ -2,27 +2,29 @@
#include "StdAfx.h"
-#include "resource.h"
-
-#include "Common/StringConvert.h"
-#include "Common/Random.h"
-#include "Common/StringConvert.h"
#include "Common/AutoPtr.h"
+#include "Common/StringConvert.h"
+#include "Windows/Error.h"
#include "Windows/FileDir.h"
#include "Windows/FileFind.h"
-#include "Windows/Thread.h"
#include "Windows/Synchronization.h"
-#include "Windows/Error.h"
+#include "Windows/Thread.h"
#include "ExtractCallback.h"
-#include "UpdateCallback100.h"
-#include "IFolder.h"
#include "FileFolderPluginOpen.h"
#include "FormatUtils.h"
+#include "IFolder.h"
+#include "LangUtils.h"
#include "Panel.h"
#include "RegistryUtils.h"
-#include "LangUtils.h"
+#include "UpdateCallback100.h"
+
+#include "App.h"
+
+#include "../Common/ExtractingFilePath.h"
+
+#include "resource.h"
using namespace NWindows;
using namespace NSynchronization;
@@ -66,20 +68,25 @@ public:
}
};
-HRESULT CPanel::OpenItemAsArchive(const UString &name,
- const UString &folderPath, const UString &filePath,
+HRESULT CPanel::OpenItemAsArchive(IInStream *inStream,
+ const CTempFileInfo &tempFileInfo,
const UString &virtualFilePath,
bool &encrypted)
{
encrypted = false;
CFolderLink folderLink;
- if (!NFile::NFind::FindFile(filePath, folderLink.FileInfo))
- return E_FAIL;
- if (folderLink.FileInfo.IsDir())
- return S_FALSE;
+ (CTempFileInfo &)folderLink = tempFileInfo;
+ if (inStream)
+ folderLink.IsVirtual = true;
+ else
+ {
+ if (!folderLink.FileInfo.Find(folderLink.FilePath))
+ return ::GetLastError();
+ if (folderLink.FileInfo.IsDir())
+ return S_FALSE;
+ folderLink.IsVirtual = false;
+ }
- folderLink.FilePath = filePath;
- folderLink.FolderPath = folderPath;
folderLink.VirtualPath = virtualFilePath;
CMyComPtr<IFolderFolder> newFolder;
@@ -90,13 +97,14 @@ HRESULT CPanel::OpenItemAsArchive(const UString &name,
NDLL::CLibrary library;
UString password;
- RINOK(OpenFileFolderPlugin(filePath, &library, &newFolder, GetParent(), encrypted, password));
+ RINOK(OpenFileFolderPlugin(inStream,
+ folderLink.FilePath.IsEmpty() ? virtualFilePath : folderLink.FilePath,
+ &library, &newFolder, GetParent(), encrypted, password));
folderLink.Password = password;
folderLink.UsePassword = encrypted;
folderLink.ParentFolder = _folder;
- folderLink.ItemName = name;
_parentFolders.Add(folderLink);
_parentFolders.Back().Library.Attach(_library.Detach());
@@ -110,19 +118,20 @@ HRESULT CPanel::OpenItemAsArchive(const UString &name,
return S_OK;
}
-HRESULT CPanel::OpenItemAsArchive(const UString &name)
+HRESULT CPanel::OpenItemAsArchive(const UString &name, bool &encrypted)
{
- bool encrypted;
- return OpenItemAsArchive(name, _currentFolderPrefix,
- _currentFolderPrefix + name,
- _currentFolderPrefix + name,
- encrypted);
+ CTempFileInfo tfi;
+ tfi.ItemName = name;
+ tfi.FolderPath = _currentFolderPrefix;
+ tfi.FilePath = _currentFolderPrefix + name;
+ return OpenItemAsArchive(NULL, tfi, _currentFolderPrefix + name, encrypted);
}
HRESULT CPanel::OpenItemAsArchive(int index)
{
CDisableTimerProcessing disableTimerProcessing1(*this);
- RINOK(OpenItemAsArchive(GetItemRelPath(index)));
+ bool encrypted;
+ RINOK(OpenItemAsArchive(GetItemRelPath(index), encrypted));
RefreshListCtrl();
return S_OK;
}
@@ -132,12 +141,11 @@ HRESULT CPanel::OpenParentArchiveFolder()
CDisableTimerProcessing disableTimerProcessing1(*this);
if (_parentFolders.Size() < 2)
return S_OK;
- CFolderLink &folderLink = _parentFolders.Back();
+ const CFolderLink &folderLink = _parentFolders.Back();
NFind::CFileInfoW newFileInfo;
- if (NFind::FindFile(folderLink.FilePath, newFileInfo))
+ if (newFileInfo.Find(folderLink.FilePath))
{
- if (newFileInfo.Size != folderLink.FileInfo.Size ||
- CompareFileTime(&newFileInfo.MTime, &folderLink.FileInfo.MTime) != 0)
+ if (folderLink.WasChanged(newFileInfo))
{
UString message = MyFormatNew(IDS_WANT_UPDATE_MODIFIED_FILE,
0x03020280, folderLink.ItemName);
@@ -166,7 +174,7 @@ static const wchar_t *kStartExtensions[] =
L"docx", L"docm", L"dotx", L"dotm", L"xlsx", L"xlsm", L"xltx", L"xltm", L"xlsb",
L"xlam", L"pptx", L"pptm", L"potx", L"potm", L"ppam", L"ppsx", L"ppsm", L"xsn",
- L"dwf",
+ L"dwf",
L"odt", L"ods",
L"wb3",
@@ -186,22 +194,8 @@ static bool DoItemAlwaysStart(const UString &name)
return false;
}
-static HANDLE StartEditApplication(const UString &path, HWND window)
+static HRESULT MyCreateProcess(const UString &command, HANDLE *hProcess)
{
- UString command;
- ReadRegEditor(command);
- if (command.IsEmpty())
- {
- if (!MyGetWindowsDirectory(command))
- return 0;
- NFile::NName::NormalizeDirPathPrefix(command);
- command += L"notepad.exe";
- }
- command = UString(L"\"") + command + UString(L"\"");
- command += L" \"";
- command += UString(path);
- command += L"\"";
-
PROCESS_INFORMATION processInformation;
BOOL result;
#ifndef _UNICODE
@@ -235,16 +229,96 @@ static HANDLE StartEditApplication(const UString &path, HWND window)
NULL, NULL, FALSE, 0, NULL, NULL, &startupInfo, &processInformation);
}
- if (result != FALSE)
+ if (result == 0)
+ return ::GetLastError();
+
+ ::CloseHandle(processInformation.hThread);
+ *hProcess = processInformation.hProcess;
+ return S_OK;
+}
+
+static HRESULT MyCreateProcess(const UString &command)
+{
+ HANDLE hProcess;
+ HRESULT res = MyCreateProcess(command, &hProcess);
+ if (res == SZ_OK)
+ ::CloseHandle(hProcess);
+ return res;
+}
+
+static HANDLE StartEditApplication(const UString &path, HWND window)
+{
+ UString command;
+ ReadRegEditor(command);
+ if (command.IsEmpty())
{
- ::CloseHandle(processInformation.hThread);
- return processInformation.hProcess;
+ if (!MyGetWindowsDirectory(command))
+ return 0;
+ NFile::NName::NormalizeDirPathPrefix(command);
+ command += L"notepad.exe";
}
+ command = UString(L"\"") + command + UString(L"\"");
+ command += L" \"";
+ command += path;
+ command += L"\"";
+
+ HANDLE hProcess;
+ HRESULT res = MyCreateProcess(command, &hProcess);
+ if (res == SZ_OK)
+ return hProcess;
::MessageBoxW(window, LangString(IDS_CANNOT_START_EDITOR, 0x03020282),
L"7-Zip", MB_OK | MB_ICONSTOP);
return 0;
}
+void CApp::DiffFiles()
+{
+ const CPanel &panel = GetFocusedPanel();
+
+ CRecordVector<UInt32> indices;
+ panel.GetSelectedItemsIndices(indices);
+
+ UString path1, path2;
+ if (indices.Size() == 2)
+ {
+ path1 = panel.GetItemFullPath(indices[0]);
+ path2 = panel.GetItemFullPath(indices[1]);
+ }
+ else if (indices.Size() == 1 && NumPanels >= 2)
+ {
+ const CPanel &destPanel = Panels[1 - LastFocusedPanel];
+ path1 = panel.GetItemFullPath(indices[0]);
+ const UString relPath = panel.GetItemRelPath(indices[0]);
+ CRecordVector<UInt32> indices2;
+ destPanel.GetSelectedItemsIndices(indices2);
+ if (indices2.Size() == 1)
+ path2 = destPanel.GetItemFullPath(indices2[0]);
+ else
+ path2 = destPanel._currentFolderPrefix + relPath;
+ }
+ else
+ return;
+
+ UString command;
+ ReadRegDiff(command);
+ if (command.IsEmpty())
+ return;
+
+ command = UString(L"\"") + command + UString(L"\"");
+ command += L" \"";
+ command += path1;
+ command += L"\"";
+
+ command += L" \"";
+ command += path2;
+ command += L"\"";
+
+ HRESULT res = MyCreateProcess(command);
+ if (res == SZ_OK)
+ return;
+ ::MessageBoxW(_window, LangString(IDS_CANNOT_START_EDITOR, 0x03020282), L"7-Zip", MB_OK | MB_ICONSTOP);
+}
+
#ifndef _UNICODE
typedef BOOL (WINAPI * ShellExecuteExWP)(LPSHELLEXECUTEINFOW lpExecInfo);
#endif
@@ -314,14 +388,16 @@ void CPanel::EditItem(int index)
OpenItemInArchive(index, false, true, true);
return;
}
- HANDLE hProcess = StartEditApplication(_currentFolderPrefix + GetItemRelPath(index), (HWND)*this);
+ HANDLE hProcess = StartEditApplication(GetItemFullPath(index), (HWND)*this);
if (hProcess != 0)
::CloseHandle(hProcess);
}
void CPanel::OpenFolderExternal(int index)
{
- HANDLE hProcess = StartApplication(GetFsPath(), GetFsPath() + GetItemRelPath(index), (HWND)*this);
+ UString fsPrefix = GetFsPath();
+ HANDLE hProcess = StartApplication(fsPrefix,
+ fsPrefix + GetItemRelPath(index) + WCHAR_PATH_SEPARATOR, (HWND)*this);
if (hProcess != 0)
::CloseHandle(hProcess);
}
@@ -428,7 +504,7 @@ public:
static THREAD_FUNC_DECL MyThreadFunction(void *param)
{
CMyAutoPtr<CTmpProcessInfo> tmpProcessInfoPtr((CTmpProcessInfo *)param);
- CTmpProcessInfo *tmpProcessInfo = tmpProcessInfoPtr.get();
+ const CTmpProcessInfo *tmpProcessInfo = tmpProcessInfoPtr.get();
HANDLE hProcess = tmpProcessInfo->ProcessHandle;
HANDLE events[2] = { g_ExitEventLauncher._exitEvent, hProcess};
@@ -440,10 +516,9 @@ static THREAD_FUNC_DECL MyThreadFunction(void *param)
return 1;
Sleep(200);
NFind::CFileInfoW newFileInfo;
- if (NFind::FindFile(tmpProcessInfo->FilePath, newFileInfo))
+ if (newFileInfo.Find(tmpProcessInfo->FilePath))
{
- if (newFileInfo.Size != tmpProcessInfo->FileInfo.Size ||
- CompareFileTime(&newFileInfo.MTime, &tmpProcessInfo->FileInfo.MTime) != 0)
+ if (tmpProcessInfo->WasChanged(newFileInfo))
{
UString message = MyFormatNew(IDS_WANT_UPDATE_MODIFIED_FILE,
0x03020280, tmpProcessInfo->ItemName);
@@ -478,12 +553,51 @@ void CPanel::OpenItemInArchive(int index, bool tryInternal, bool tryExternal, bo
return;
}
+ bool tryAsArchive = tryInternal && (!tryExternal || !DoItemAlwaysStart(name));
+
+ UString fullVirtPath = _currentFolderPrefix + name;
+
NFile::NDirectory::CTempDirectoryW tempDirectory;
tempDirectory.Create(kTempDirPrefix);
UString tempDir = tempDirectory.GetPath();
UString tempDirNorm = tempDir;
NFile::NName::NormalizeDirPathPrefix(tempDirNorm);
+ UString tempFilePath = tempDirNorm + GetCorrectFsPath(name);
+
+ CTempFileInfo tempFileInfo;
+ tempFileInfo.ItemName = name;
+ tempFileInfo.FolderPath = tempDir;
+ tempFileInfo.FilePath = tempFilePath;
+ tempFileInfo.NeedDelete = true;
+
+ if (tryAsArchive)
+ {
+ CMyComPtr<IInArchiveGetStream> getStream;
+ _folder.QueryInterface(IID_IInArchiveGetStream, &getStream);
+ if (getStream)
+ {
+ CMyComPtr<ISequentialInStream> subSeqStream;
+ getStream->GetStream(index, &subSeqStream);
+ if (subSeqStream)
+ {
+ CMyComPtr<IInStream> subStream;
+ subSeqStream.QueryInterface(IID_IInStream, &subStream);
+ if (subStream)
+ {
+ bool encrypted;
+ if (OpenItemAsArchive(subStream, tempFileInfo, fullVirtPath, encrypted) == S_OK)
+ {
+ tempDirectory.DisableDeleting();
+ RefreshListCtrl();
+ return;
+ }
+ }
+ }
+ }
+ }
+
+
CRecordVector<UInt32> indices;
indices.Add(index);
@@ -516,32 +630,29 @@ void CPanel::OpenItemInArchive(int index, bool tryInternal, bool tryExternal, bo
return;
}
- UString tempFilePath = tempDirNorm + name;
+
+ if (tryAsArchive)
+ {
+ bool encrypted;
+ if (OpenItemAsArchive(NULL, tempFileInfo, fullVirtPath, encrypted) == S_OK)
+ {
+ tempDirectory.DisableDeleting();
+ RefreshListCtrl();
+ return;
+ }
+ }
CMyAutoPtr<CTmpProcessInfo> tmpProcessInfoPtr(new CTmpProcessInfo());
CTmpProcessInfo *tmpProcessInfo = tmpProcessInfoPtr.get();
tmpProcessInfo->FolderPath = tempDir;
tmpProcessInfo->FilePath = tempFilePath;
+ tmpProcessInfo->NeedDelete = true;
tmpProcessInfo->UsePassword = usePassword;
tmpProcessInfo->Password = password;
- if (!NFind::FindFile(tempFilePath, tmpProcessInfo->FileInfo))
+ if (!tmpProcessInfo->FileInfo.Find(tempFilePath))
return;
- if (tryInternal)
- {
- if (!tryExternal || !DoItemAlwaysStart(name))
- {
- bool encrypted;
- if (OpenItemAsArchive(name, tempDir, tempFilePath,
- _currentFolderPrefix + name, encrypted) == S_OK)
- {
- RefreshListCtrl();
- return;
- }
- }
- }
-
CTmpProcessInfoRelease tmpProcessInfoRelease(*tmpProcessInfo);
if (!tryExternal)
diff --git a/CPP/7zip/UI/FileManager/PanelItems.cpp b/CPP/7zip/UI/FileManager/PanelItems.cpp
index 58e14759..7ea9585a 100755
--- a/CPP/7zip/UI/FileManager/PanelItems.cpp
+++ b/CPP/7zip/UI/FileManager/PanelItems.cpp
@@ -2,6 +2,8 @@
#include "StdAfx.h"
+#include "../../../../C/Sort.h"
+
#include "Common/StringConvert.h"
#include "Windows/Menu.h"
@@ -17,11 +19,6 @@
#include "PropertyName.h"
#include "RootFolder.h"
-extern "C"
-{
- #include "../../../../C/Sort.h"
-}
-
using namespace NWindows;
static int GetColumnAlign(PROPID propID, VARTYPE varType)
@@ -137,9 +134,9 @@ void CPanel::InitColumns()
_visibleProperties.Clear();
for (i = 0; i < _properties.Size(); i++)
{
- const CItemProperty &property = _properties[i];
- if (property.IsVisible)
- _visibleProperties.Add(property);
+ const CItemProperty &prop = _properties[i];
+ if (prop.IsVisible)
+ _visibleProperties.Add(prop);
}
// _sortIndex = 0;
@@ -162,14 +159,14 @@ void CPanel::InitColumns()
void CPanel::InsertColumn(int index)
{
- const CItemProperty &property = _visibleProperties[index];
+ const CItemProperty &prop = _visibleProperties[index];
LV_COLUMNW column;
column.mask = LVCF_FMT | LVCF_WIDTH | LVCF_TEXT | LVCF_SUBITEM | LVCF_ORDER;
- column.cx = property.Width;
- column.fmt = GetColumnAlign(property.ID, property.Type);
- column.iOrder = property.Order;
+ column.cx = prop.Width;
+ column.fmt = GetColumnAlign(prop.ID, prop.Type);
+ column.iOrder = prop.Order;
column.iSubItem = index;
- column.pszText = (wchar_t *)(const wchar_t *)property.Name;
+ column.pszText = (wchar_t *)(const wchar_t *)prop.Name;
_listView.InsertColumn(index, &column);
}
@@ -344,8 +341,8 @@ void CPanel::RefreshListCtrl(const UString &focusedName, int focusedPos, bool se
item.iSubItem = subItem++;
item.lParam = kParentIndex;
item.pszText = (wchar_t *)(const wchar_t *)itemName;
- UInt32 attributes = FILE_ATTRIBUTE_DIRECTORY;
- item.iImage = _extToIconMap.GetIconIndex(attributes, itemName);
+ UInt32 attrib = FILE_ATTRIBUTE_DIRECTORY;
+ item.iImage = _extToIconMap.GetIconIndex(attrib, itemName);
if (item.iImage < 0)
item.iImage = 0;
if(_listView.InsertItem(&item) == -1)
@@ -402,16 +399,13 @@ void CPanel::RefreshListCtrl(const UString &focusedName, int focusedPos, bool se
else
item.pszText = (wchar_t *)(const wchar_t *)itemName;
- NCOM::CPropVariant propVariant;
- _folder->GetProperty(i, kpidAttrib, &propVariant);
- UInt32 attributes = 0;
- if (propVariant.vt == VT_UI4)
- attributes = propVariant.ulVal;
- else
- {
- if (IsItemFolder(i))
- attributes |= FILE_ATTRIBUTE_DIRECTORY;
- }
+ NCOM::CPropVariant prop;
+ _folder->GetProperty(i, kpidAttrib, &prop);
+ UInt32 attrib = 0;
+ if (prop.vt == VT_UI4)
+ attrib = prop.ulVal;
+ else if (IsItemFolder(i))
+ attrib |= FILE_ATTRIBUTE_DIRECTORY;
bool defined = false;
@@ -425,12 +419,12 @@ void CPanel::RefreshListCtrl(const UString &focusedName, int focusedPos, bool se
if (_currentFolderPrefix.IsEmpty())
{
int iconIndexTemp;
- GetRealIconIndex(itemName + WCHAR_PATH_SEPARATOR, attributes, iconIndexTemp);
+ GetRealIconIndex(itemName + WCHAR_PATH_SEPARATOR, attrib, iconIndexTemp);
item.iImage = iconIndexTemp;
}
else
{
- item.iImage = _extToIconMap.GetIconIndex(attributes, itemName);
+ item.iImage = _extToIconMap.GetIconIndex(attrib, itemName);
}
}
if (item.iImage < 0)
@@ -572,7 +566,7 @@ void CPanel::OpenSelectedItems(bool tryInternal)
if (focusedItem >= 0)
{
int realIndex = GetRealItemIndex(focusedItem);
- if (realIndex == kParentIndex && (tryInternal || indices.Size() == 0) &&
+ if (realIndex == kParentIndex && (tryInternal || indices.Size() == 0) &&
_listView.GetItemState(focusedItem, LVIS_SELECTED) == LVIS_SELECTED)
indices.Insert(0, realIndex);
}
@@ -605,24 +599,24 @@ UString CPanel::GetItemName(int itemIndex) const
{
if (itemIndex == kParentIndex)
return L"..";
- NCOM::CPropVariant propVariant;
- if (_folder->GetProperty(itemIndex, kpidName, &propVariant) != S_OK)
+ NCOM::CPropVariant prop;
+ if (_folder->GetProperty(itemIndex, kpidName, &prop) != S_OK)
throw 2723400;
- if (propVariant.vt != VT_BSTR)
+ if (prop.vt != VT_BSTR)
throw 2723401;
- return (propVariant.bstrVal);
+ return prop.bstrVal;
}
UString CPanel::GetItemPrefix(int itemIndex) const
{
if (itemIndex == kParentIndex)
return UString();
- NCOM::CPropVariant propVariant;
- if (_folder->GetProperty(itemIndex, kpidPrefix, &propVariant) != S_OK)
+ NCOM::CPropVariant prop;
+ if (_folder->GetProperty(itemIndex, kpidPrefix, &prop) != S_OK)
throw 2723400;
UString prefix;
- if (propVariant.vt == VT_BSTR)
- prefix = propVariant.bstrVal;
+ if (prop.vt == VT_BSTR)
+ prefix = prop.bstrVal;
return prefix;
}
@@ -631,17 +625,21 @@ UString CPanel::GetItemRelPath(int itemIndex) const
return GetItemPrefix(itemIndex) + GetItemName(itemIndex);
}
+UString CPanel::GetItemFullPath(int itemIndex) const
+{
+ return _currentFolderPrefix + GetItemRelPath(itemIndex);
+}
bool CPanel::IsItemFolder(int itemIndex) const
{
if (itemIndex == kParentIndex)
return true;
- NCOM::CPropVariant propVariant;
- if (_folder->GetProperty(itemIndex, kpidIsDir, &propVariant) != S_OK)
+ NCOM::CPropVariant prop;
+ if (_folder->GetProperty(itemIndex, kpidIsDir, &prop) != S_OK)
throw 2723400;
- if (propVariant.vt == VT_BOOL)
- return VARIANT_BOOLToBool(propVariant.boolVal);
- if (propVariant.vt == VT_EMPTY)
+ if (prop.vt == VT_BOOL)
+ return VARIANT_BOOLToBool(prop.boolVal);
+ if (prop.vt == VT_EMPTY)
return false;
return false;
}
@@ -650,12 +648,12 @@ UINT64 CPanel::GetItemSize(int itemIndex) const
{
if (itemIndex == kParentIndex)
return 0;
- NCOM::CPropVariant propVariant;
- if (_folder->GetProperty(itemIndex, kpidSize, &propVariant) != S_OK)
+ NCOM::CPropVariant prop;
+ if (_folder->GetProperty(itemIndex, kpidSize, &prop) != S_OK)
throw 2723400;
- if (propVariant.vt == VT_EMPTY)
+ if (prop.vt == VT_EMPTY)
return 0;
- return ConvertPropVariantToUInt64(propVariant);
+ return ConvertPropVariantToUInt64(prop);
}
void CPanel::ReadListViewInfo()
@@ -670,13 +668,13 @@ void CPanel::SaveListViewInfo()
int i;
for(i = 0; i < _visibleProperties.Size(); i++)
{
- CItemProperty &property = _visibleProperties[i];
+ CItemProperty &prop = _visibleProperties[i];
LVCOLUMN winColumnInfo;
winColumnInfo.mask = LVCF_ORDER | LVCF_WIDTH;
if (!_listView.GetColumn(i, &winColumnInfo))
throw 1;
- property.Order = winColumnInfo.iOrder;
- property.Width = winColumnInfo.cx;
+ prop.Order = winColumnInfo.iOrder;
+ prop.Width = winColumnInfo.cx;
}
CListViewInfo viewInfo;
@@ -687,22 +685,22 @@ void CPanel::SaveListViewInfo()
_visibleProperties.Sort();
for(i = 0; i < _visibleProperties.Size(); i++)
{
- const CItemProperty &property = _visibleProperties[i];
+ const CItemProperty &prop = _visibleProperties[i];
CColumnInfo columnInfo;
- columnInfo.IsVisible = property.IsVisible;
- columnInfo.PropID = property.ID;
- columnInfo.Width = property.Width;
+ columnInfo.IsVisible = prop.IsVisible;
+ columnInfo.PropID = prop.ID;
+ columnInfo.Width = prop.Width;
viewInfo.Columns.Add(columnInfo);
}
for(i = 0; i < _properties.Size(); i++)
{
- const CItemProperty &property = _properties[i];
- if (!property.IsVisible)
+ const CItemProperty &prop = _properties[i];
+ if (!prop.IsVisible)
{
CColumnInfo columnInfo;
- columnInfo.IsVisible = property.IsVisible;
- columnInfo.PropID = property.ID;
- columnInfo.Width = property.Width;
+ columnInfo.IsVisible = prop.IsVisible;
+ columnInfo.PropID = prop.ID;
+ columnInfo.Width = prop.Width;
viewInfo.Columns.Add(columnInfo);
}
}
@@ -734,32 +732,32 @@ bool CPanel::OnRightClick(LPNMITEMACTIVATE itemActiveate, LRESULT &result)
const int kCommandStart = 100;
for(int i = 0; i < _properties.Size(); i++)
{
- const CItemProperty &property = _properties[i];
+ const CItemProperty &prop = _properties[i];
UINT flags = MF_STRING;
- if (property.IsVisible)
+ if (prop.IsVisible)
flags |= MF_CHECKED;
if (i == 0)
flags |= MF_GRAYED;
- menu.AppendItem(flags, kCommandStart + i, GetSystemString(property.Name));
+ menu.AppendItem(flags, kCommandStart + i, prop.Name);
}
int menuResult = menu.Track(TPM_LEFTALIGN | TPM_RETURNCMD | TPM_NONOTIFY,
point.x, point.y, _listView);
if (menuResult >= kCommandStart && menuResult <= kCommandStart + _properties.Size())
{
int index = menuResult - kCommandStart;
- CItemProperty &property = _properties[index];
- property.IsVisible = !property.IsVisible;
+ CItemProperty &prop = _properties[index];
+ prop.IsVisible = !prop.IsVisible;
- if (property.IsVisible)
+ if (prop.IsVisible)
{
int prevVisibleSize = _visibleProperties.Size();
- property.Order = prevVisibleSize;
- _visibleProperties.Add(property);
+ prop.Order = prevVisibleSize;
+ _visibleProperties.Add(prop);
InsertColumn(prevVisibleSize);
}
else
{
- int visibleIndex = _visibleProperties.FindItemWithID(property.ID);
+ int visibleIndex = _visibleProperties.FindItemWithID(prop.ID);
_visibleProperties.Delete(visibleIndex);
/*
if (_sortIndex == index)
@@ -768,7 +766,7 @@ bool CPanel::OnRightClick(LPNMITEMACTIVATE itemActiveate, LRESULT &result)
_ascending = true;
}
*/
- if (_sortID == property.ID)
+ if (_sortID == prop.ID)
{
_sortID = kpidName;
_ascending = true;
@@ -794,11 +792,10 @@ void CPanel::OnTimer()
CMyComPtr<IFolderWasChanged> folderWasChanged;
if (_folder.QueryInterface(IID_IFolderWasChanged, &folderWasChanged) != S_OK)
return;
- INT32 wasChanged;
+ Int32 wasChanged;
if (folderWasChanged->WasChanged(&wasChanged) != S_OK)
return;
if (wasChanged == 0)
return;
OnReload();
}
-
diff --git a/CPP/7zip/UI/FileManager/PanelListNotify.cpp b/CPP/7zip/UI/FileManager/PanelListNotify.cpp
index 21600a68..aee4759e 100755
--- a/CPP/7zip/UI/FileManager/PanelListNotify.cpp
+++ b/CPP/7zip/UI/FileManager/PanelListNotify.cpp
@@ -18,6 +18,7 @@
using namespace NWindows;
+/*
static UString ConvertSizeToStringShort(UInt64 value)
{
wchar_t s[32];
@@ -50,6 +51,7 @@ static UString ConvertSizeToStringShort(UInt64 value)
s[p++] = L'\0';
return s;
}
+*/
UString ConvertSizeToString(UInt64 value)
{
@@ -116,7 +118,7 @@ LRESULT CPanel::SetItemText(LVITEMW &item)
/*
{
NCOM::CPropVariant property;
- if(propID == kpidType)
+ if (propID == kpidType)
string = GetFileType(index);
else
{
@@ -150,13 +152,18 @@ LRESULT CPanel::SetItemText(LVITEMW &item)
if (_folder->GetProperty(realIndex, propID, &prop) != S_OK)
throw 2723407;
- if ((propID == kpidSize || propID == kpidPackSize || propID == kpidClusterSize ||
- propID == kpidNumSubDirs || propID == kpidNumSubFiles) &&
- (prop.vt == VT_UI8 || prop.vt == VT_UI4))
+ if ((prop.vt == VT_UI8 || prop.vt == VT_UI4) && (
+ propID == kpidSize ||
+ propID == kpidPackSize ||
+ propID == kpidNumSubDirs ||
+ propID == kpidNumSubFiles ||
+ propID == kpidPosition ||
+ propID == kpidNumBlocks ||
+ propID == kpidClusterSize ||
+ propID == kpidTotalSize ||
+ propID == kpidFreeSpace
+ ))
s = ConvertSizeToString(ConvertPropVariantToUInt64(prop));
- else if ((propID == kpidTotalSize || propID == kpidFreeSpace) &&
- (prop.vt == VT_UI8 || prop.vt == VT_UI4))
- s = ConvertSizeToStringShort(ConvertPropVariantToUInt64(prop));
else
{
s = ConvertPropertyToString(prop, propID, false);
@@ -164,9 +171,9 @@ LRESULT CPanel::SetItemText(LVITEMW &item)
s.Replace(wchar_t(0xD), L' ');
}
int size = item.cchTextMax;
- if(size > 0)
+ if (size > 0)
{
- if(s.Length() + 1 > size)
+ if (s.Length() + 1 > size)
s = s.Left(size - 1);
MyStringCopy(item.pszText, (const wchar_t *)s);
}
@@ -183,7 +190,7 @@ void CPanel::OnItemChanged(NMLISTVIEW *item)
bool oldSelected = (item->uOldState & LVIS_SELECTED) != 0;
bool newSelected = (item->uNewState & LVIS_SELECTED) != 0;
// Don't change this code. It works only with such check
- if(oldSelected != newSelected)
+ if (oldSelected != newSelected)
_selectedStatusVector[index] = newSelected;
}
@@ -218,7 +225,7 @@ bool CPanel::OnNotifyList(LPNMHDR header, LRESULT &result)
//is the sub-item information being requested?
- if((dispInfo->item.mask & LVIF_TEXT) != 0 ||
+ if ((dispInfo->item.mask & LVIF_TEXT) != 0 ||
(dispInfo->item.mask & LVIF_IMAGE) != 0)
SetItemText(dispInfo->item);
return false;
@@ -290,8 +297,8 @@ bool CPanel::OnNotifyList(LPNMHDR header, LRESULT &result)
// we need SetFocusToList, if we drag-select items from other panel.
SetFocusToList();
RefreshStatusBar();
- if(_mySelectMode)
- if(g_ComCtl32Version >= MAKELONG(71, 4))
+ if (_mySelectMode)
+ if (g_ComCtl32Version >= MAKELONG(71, 4))
OnLeftClick((LPNMITEMACTIVATE)header);
return false;
}
diff --git a/CPP/7zip/UI/FileManager/PanelMenu.cpp b/CPP/7zip/UI/FileManager/PanelMenu.cpp
index ab48bbc7..2672f694 100755
--- a/CPP/7zip/UI/FileManager/PanelMenu.cpp
+++ b/CPP/7zip/UI/FileManager/PanelMenu.cpp
@@ -1,21 +1,23 @@
#include "StdAfx.h"
#include "Common/StringConvert.h"
-#include "Windows/Menu.h"
+
#include "Windows/COM.h"
-#include "Windows/PropVariant.h"
#include "Windows/Clipboard.h"
+#include "Windows/Menu.h"
+#include "Windows/PropVariant.h"
#include "Windows/PropVariantConversions.h"
+
#include "../Common/PropIDUtils.h"
#include "../../PropID.h"
-#include "Panel.h"
-#include "PluginInterface.h"
-#include "MyLoadMenu.h"
#include "App.h"
#include "LangUtils.h"
-#include "resource.h"
+#include "MyLoadMenu.h"
+#include "PluginInterface.h"
#include "PropertyName.h"
+
+#include "resource.h"
#include "PropertyNameRes.h"
using namespace NWindows;
@@ -30,7 +32,7 @@ static const UINT kSystemStartMenuID = kPluginMenuStartID + 100;
void CPanel::InvokeSystemCommand(const char *command)
{
NCOM::CComInitializer comInitializer;
- if (!IsFSFolder() && !IsFSDrivesFolder())
+ if (!IsFsOrPureDrivesFolder())
return;
CRecordVector<UInt32> operatedIndices;
GetOperatedItemIndices(operatedIndices);
@@ -58,26 +60,28 @@ static void AddPropertyString(PROPID propID, const wchar_t *nameBSTR,
{
if (prop.vt != VT_EMPTY)
{
- const UString name = GetNameOfProperty(propID, nameBSTR);
UString val;
- if ((
+ if ((prop.vt == VT_UI8 || prop.vt == VT_UI4) && (
propID == kpidSize ||
propID == kpidPackSize ||
propID == kpidNumSubDirs ||
propID == kpidNumSubFiles ||
propID == kpidNumBlocks ||
+ propID == kpidClusterSize ||
+ propID == kpidTotalSize ||
+ propID == kpidFreeSpace ||
propID == kpidPhySize ||
propID == kpidHeadersSize ||
- propID == kpidClusterSize
- ) && (prop.vt == VT_UI8 || prop.vt == VT_UI4))
+ propID == kpidFreeSpace
+ ))
val = ConvertSizeToString(ConvertPropVariantToUInt64(prop));
else
val = ConvertPropertyToString(prop, propID);
if (!val.IsEmpty())
{
- s += name;
+ s += GetNameOfProperty(propID, nameBSTR);
s += kPropValueSeparator;
/*
if (propID == kpidComment)
@@ -129,7 +133,7 @@ void CPanel::Properties()
message += kSeparator;
}
- message += LangString(IDS_PROPERTY_FILE_TYPE, 0x02000214);
+ message += LangString(IDS_PROP_FILE_TYPE, 0x02000214);
message += kPropValueSeparator;
message += GetFolderTypeID();
message += L"\n";
diff --git a/CPP/7zip/UI/FileManager/PanelOperations.cpp b/CPP/7zip/UI/FileManager/PanelOperations.cpp
index c3b5d69d..9a60fb1a 100755
--- a/CPP/7zip/UI/FileManager/PanelOperations.cpp
+++ b/CPP/7zip/UI/FileManager/PanelOperations.cpp
@@ -2,25 +2,25 @@
#include "StdAfx.h"
-#include "resource.h"
-
-#include "Panel.h"
-
-#include "Common/StringConvert.h"
#include "Common/DynamicBuffer.h"
+#include "Common/StringConvert.h"
+
+#include "Windows/COM.h"
#include "Windows/FileDir.h"
+#include "Windows/PropVariant.h"
#include "Windows/ResourceString.h"
#include "Windows/Thread.h"
-#include "Windows/COM.h"
#include "ComboDialog.h"
#include "FSFolder.h"
-#include "LangUtils.h"
#include "FormatUtils.h"
-
+#include "LangUtils.h"
+#include "Panel.h"
#include "UpdateCallback100.h"
+#include "resource.h"
+
using namespace NWindows;
using namespace NFile;
diff --git a/CPP/7zip/UI/FileManager/PanelSplitFile.cpp b/CPP/7zip/UI/FileManager/PanelSplitFile.cpp
index 36146d7a..d1531957 100755
--- a/CPP/7zip/UI/FileManager/PanelSplitFile.cpp
+++ b/CPP/7zip/UI/FileManager/PanelSplitFile.cpp
@@ -2,30 +2,25 @@
#include "StdAfx.h"
-#include "resource.h"
-
-extern "C"
-{
- #include "../../../../C/Alloc.h"
-}
+#include "../../../../C/Alloc.h"
-#include "Common/Types.h"
#include "Common/IntToString.h"
-// #include "Windows/COM.h"
#include "Windows/FileIO.h"
#include "Windows/FileFind.h"
#include "Windows/Thread.h"
-#include "ProgressDialog2.h"
-#include "SplitDialog.h"
-#include "CopyDialog.h"
#include "../GUI/ExtractRes.h"
-#include "SplitUtils.h"
+#include "resource.h"
+
#include "App.h"
+#include "CopyDialog.h"
#include "FormatUtils.h"
#include "LangUtils.h"
+#include "ProgressDialog2.h"
+#include "SplitDialog.h"
+#include "SplitUtils.h"
using namespace NWindows;
@@ -227,7 +222,7 @@ void CApp::Split()
return;
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(srcPath + itemName, fileInfo))
+ if (!fileInfo.Find(srcPath + itemName))
{
srcPanel.MessageBoxMyError(L"Can not find file");
return;
@@ -422,7 +417,7 @@ void CApp::Combine()
for (;;)
{
NFile::NFind::CFileInfoW fileInfo;
- if (!NFile::NFind::FindFile(srcPath + nextName, fileInfo) || fileInfo.IsDir())
+ if (!fileInfo.Find(srcPath + nextName) || fileInfo.IsDir())
break;
combiner.Names.Add(nextName);
combiner.TotalSize += fileInfo.Size;
@@ -490,7 +485,7 @@ void CApp::Combine()
NFile::NFind::CFileInfoW fileInfo;
UString destFilePath = path + outName;
combiner.OutputPath = destFilePath;
- if (NFile::NFind::FindFile(destFilePath, fileInfo))
+ if (fileInfo.Find(destFilePath))
{
srcPanel.MessageBoxMyError(MyFormatNew(IDS_FILE_EXIST, 0x03020A04, destFilePath));
return;
diff --git a/CPP/7zip/UI/FileManager/PhysDriveFolder.cpp b/CPP/7zip/UI/FileManager/PhysDriveFolder.cpp
index 750f2e02..12b7dce8 100755
--- a/CPP/7zip/UI/FileManager/PhysDriveFolder.cpp
+++ b/CPP/7zip/UI/FileManager/PhysDriveFolder.cpp
@@ -2,22 +2,21 @@
#include "StdAfx.h"
-extern "C"
-{
- #include "../../../../C/Alloc.h"
-}
+#include "../../../../C/Alloc.h"
+
+#include "Common/Buffer.h"
-#include "PhysDriveFolder.h"
#include "Windows/PropVariant.h"
#include "Windows/FileDevice.h"
#include "Windows/FileSystem.h"
#include "../../PropID.h"
+#include "PhysDriveFolder.h"
+
using namespace NWindows;
static const UInt32 kBufferSize = (4 << 20);
-
static STATPROPSTG kProperties[] =
{
{ NULL, kpidName, VT_BSTR},
@@ -177,7 +176,8 @@ struct CPhysTempBuffer
~CPhysTempBuffer() { MyFree(buffer); }
};
-HRESULT CopyFileSpec(LPCWSTR fromPath, LPCWSTR toPath, bool writeToDisk, UInt64 fileSize, UInt32 bufferSize, IProgress *progress)
+HRESULT CopyFileSpec(LPCWSTR fromPath, LPCWSTR toPath, bool writeToDisk, UInt64 fileSize,
+ UInt32 bufferSize, UInt64 progressStart, IProgress *progress)
{
NFile::NIO::CInFile inFile;
if (!inFile.Open(fromPath))
@@ -203,7 +203,8 @@ HRESULT CopyFileSpec(LPCWSTR fromPath, LPCWSTR toPath, bool writeToDisk, UInt64
for (UInt64 pos = 0; pos < fileSize;)
{
- RINOK(progress->SetCompleted(&pos));
+ UInt64 progressCur = progressStart + pos;
+ RINOK(progress->SetCompleted(&progressCur));
UInt64 rem = fileSize - pos;
UInt32 curSize = (UInt32)MyMin(rem, (UInt64)bufferSize);
UInt32 processedSize;
@@ -262,7 +263,7 @@ STDMETHODIMP CPhysDriveFolder::CopyTo(const UInt32 * /* indices */, UInt32 numIt
RINOK(callback->SetCurrentFilePath(GetFullPathWithName()));
UInt32 bufferSize = (_driveType == DRIVE_REMOVABLE) ? (18 << 10) * 4 : kBufferSize;
- return CopyFileSpec(GetFullPath(), destPathResult, false, fileSize, bufferSize, callback);
+ return CopyFileSpec(GetFullPath(), destPathResult, false, fileSize, bufferSize, 0, callback);
}
/////////////////////////////////////////////////
@@ -289,5 +290,6 @@ STDMETHODIMP CPhysDriveFolder::CopyFrom(
return E_NOTIMPL;
UInt32 bufferSize = (_driveType == DRIVE_REMOVABLE) ? (18 << 10) * 4 : kBufferSize;
// MessageBoxW(0, fromFolderPath, itemsPaths[0], 0);
- return CopyFileSpec((UString)fromFolderPath + itemsPaths[0], GetFullPath(), true, (UInt64)(Int64)-1, bufferSize, callback);
+ return CopyFileSpec((UString)fromFolderPath + itemsPaths[0], GetFullPath(), true, (UInt64)(Int64)-1, bufferSize, 0, callback);
}
+
diff --git a/CPP/7zip/UI/FileManager/PhysDriveFolder.h b/CPP/7zip/UI/FileManager/PhysDriveFolder.h
index 1f327966..64a36b91 100755
--- a/CPP/7zip/UI/FileManager/PhysDriveFolder.h
+++ b/CPP/7zip/UI/FileManager/PhysDriveFolder.h
@@ -5,6 +5,7 @@
#include "Common/MyString.h"
#include "Common/MyCom.h"
+#include "../../Archive/IArchive.h"
#include "IFolder.h"
@@ -32,11 +33,11 @@ public:
INTERFACE_FolderFolder(;)
INTERFACE_FolderOperations(;)
- STDMETHOD(WasChanged)(INT32 *wasChanged);
- STDMETHOD(Clone)(IFolderFolder **resultFolder);
+ STDMETHOD(WasChanged)(Int32 *wasChanged);
STDMETHOD(GetItemFullSize)(UInt32 index, PROPVARIANT *value, IProgress *progress);
+ STDMETHOD(Clone)(IFolderFolder **resultFolder);
- // STDMETHOD(GetSystemIconIndex)(UInt32 index, INT32 *iconIndex);
+ // STDMETHOD(GetSystemIconIndex)(UInt32 index, Int32 *iconIndex);
private:
UString _name;
diff --git a/CPP/7zip/UI/FileManager/ProgressDialog2.cpp b/CPP/7zip/UI/FileManager/ProgressDialog2.cpp
index e8846e68..87a1521d 100755
--- a/CPP/7zip/UI/FileManager/ProgressDialog2.cpp
+++ b/CPP/7zip/UI/FileManager/ProgressDialog2.cpp
@@ -1,10 +1,11 @@
// ProgressDialog2.cpp
#include "StdAfx.h"
-#include "resource.h"
-#include "ProgressDialog2.h"
+
#include "Common/IntToString.h"
+#include "ProgressDialog2.h"
+
using namespace NWindows;
static const UINT_PTR kTimerID = 3;
@@ -67,8 +68,8 @@ void CProgressDialog::AddToTitle(LPCWSTR s)
}
}
-static const int kTitleFileNameSizeLimit = 36;
-static const int kCurrentFileNameSizeLimit = 70;
+static const int kTitleFileNameSizeLimit = 40;
+static const int kCurrentFileNameSizeLimit = 82;
static void ReduceString(UString &s, int size)
{
@@ -143,11 +144,7 @@ void CProgressDialog::SetRange(UInt64 range)
_range = range;
_previousPos = (UInt64)(Int64)-1;
_converter.Init(range);
- m_ProgressBar.SetRange32(0 , _converter.Count(range)); // Test it for 100%
-
- wchar_t s[32];
- ConvertSizeToString(_range, s);
- SetItemText(IDC_PROGRESS_TOTAL_VALUE, s);
+ m_ProgressBar.SetRange32(0, _converter.Count(range)); // Test it for 100%
}
void CProgressDialog::SetPos(UInt64 pos)
@@ -187,19 +184,28 @@ bool CProgressDialog::OnTimer(WPARAM /* timerID */, LPARAM /* callback */)
if (ProgressSynch.GetPaused())
return true;
UInt64 total, completed, totalFiles, completedFiles, inSize, outSize;
- ProgressSynch.GetProgress(total, completed, totalFiles, completedFiles, inSize, outSize);
+ bool bytesProgressMode;
+ ProgressSynch.GetProgress(total, completed, totalFiles, completedFiles, inSize, outSize, bytesProgressMode);
UInt32 curTime = ::GetTickCount();
- if (total != _range)
- SetRange(total);
- if (total == (UInt64)(Int64)-1)
+ UInt64 progressTotal = bytesProgressMode ? total : totalFiles;
+ UInt64 progressCompleted = bytesProgressMode ? completed : completedFiles;
+
+ if (progressTotal != _range)
+ SetRange(progressTotal);
+ if (progressTotal == (UInt64)(Int64)-1)
{
SetPos(0);
- SetRange(completed);
+ SetRange(progressCompleted);
}
else
- SetPos(completed);
+ SetPos(progressCompleted);
+
+ wchar_t s[32] = { 0 };
+ if (total != (UInt64)(Int64)-1)
+ ConvertSizeToString(total, s);
+ SetItemText(IDC_PROGRESS_TOTAL_VALUE, s);
_elapsedTime += (curTime - _prevTime);
_prevTime = curTime;
diff --git a/CPP/7zip/UI/FileManager/ProgressDialog2.h b/CPP/7zip/UI/FileManager/ProgressDialog2.h
index e838ae25..3ab9f4c0 100755
--- a/CPP/7zip/UI/FileManager/ProgressDialog2.h
+++ b/CPP/7zip/UI/FileManager/ProgressDialog2.h
@@ -1,9 +1,7 @@
// ProgressDialog2.h
-#ifndef __PROGRESSDIALOG2_H
-#define __PROGRESSDIALOG2_H
-
-#include "ProgressDialog2Res.h"
+#ifndef __PROGRESS_DIALOG2_H
+#define __PROGRESS_DIALOG2_H
#include "Common/Types.h"
@@ -11,59 +9,69 @@
#include "Windows/Control/ProgressBar.h"
#include "Windows/Synchronization.h"
+#include "ProgressDialog2Res.h"
+
class CProgressSynch
{
- NWindows::NSynchronization::CCriticalSection _criticalSection;
+ NWindows::NSynchronization::CCriticalSection _cs;
bool _stopped;
bool _paused;
- UInt64 _total;
- UInt64 _completed;
+ bool _bytesProgressMode;
+
+ UInt64 _totalBytes;
+ UInt64 _curBytes;
+ UInt64 _totalFiles;
+ UInt64 _curFiles;
UInt64 _inSize;
UInt64 _outSize;
- UInt64 _totalFiles;
- UInt64 _completedFiles;
+
UString TitleFileName;
UString CurrentFileName;
+
public:
CProgressSynch():
_stopped(false), _paused(false),
- _total((UInt64)(Int64)-1),
- _completed(0),
- _totalFiles((UInt64)(Int64)-1),
- _completedFiles(0),
+ _totalBytes((UInt64)(Int64)-1), _curBytes(0),
+ _totalFiles((UInt64)(Int64)-1), _curFiles(0),
_inSize((UInt64)(Int64)-1),
- _outSize((UInt64)(Int64)-1)
+ _outSize((UInt64)(Int64)-1),
+ _bytesProgressMode(true)
{}
bool GetStopped()
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
return _stopped;
}
void SetStopped(bool value)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
_stopped = value;
}
bool GetPaused()
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
return _paused;
}
void SetPaused(bool value)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
_paused = value;
}
+ void SetBytesProgressMode(bool bytesProgressMode)
+ {
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ _bytesProgressMode = bytesProgressMode;
+ }
void SetProgress(UInt64 total, UInt64 completed)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
- _total = total;
- _completed = completed;
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ _totalBytes = total;
+ _curBytes = completed;
}
void SetRatioInfo(const UInt64 *inSize, const UInt64 *outSize)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
if (inSize)
_inSize = *inSize;
if (outSize)
@@ -71,51 +79,58 @@ public:
}
void SetPos(UInt64 completed)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
- _completed = completed;
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ _curBytes = completed;
+ }
+ void SetNumBytesTotal(UInt64 value)
+ {
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ _totalBytes = value;
}
void SetNumFilesTotal(UInt64 value)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
_totalFiles = value;
}
void SetNumFilesCur(UInt64 value)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
- _completedFiles = value;
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ _curFiles = value;
}
HRESULT ProcessStopAndPause();
HRESULT SetPosAndCheckPaused(UInt64 completed);
void GetProgress(UInt64 &total, UInt64 &completed,
- UInt64 &totalFiles, UInt64 &completedFiles,
- UInt64 &inSize, UInt64 &outSize)
+ UInt64 &totalFiles, UInt64 &curFiles,
+ UInt64 &inSize, UInt64 &outSize,
+ bool &bytesProgressMode)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
- total = _total;
- completed = _completed;
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
+ total = _totalBytes;
+ completed = _curBytes;
totalFiles = _totalFiles;
- completedFiles = _completedFiles;
+ curFiles = _curFiles;
inSize = _inSize;
outSize = _outSize;
+ bytesProgressMode = _bytesProgressMode;
}
void SetTitleFileName(const UString &fileName)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
TitleFileName = fileName;
}
void GetTitleFileName(UString &fileName)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
fileName = TitleFileName;
}
void SetCurrentFileName(const UString &fileName)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
CurrentFileName = fileName;
}
void GetCurrentFileName(UString &fileName)
{
- NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
+ NWindows::NSynchronization::CCriticalSectionLock lock(_cs);
fileName = CurrentFileName;
}
};
diff --git a/CPP/7zip/UI/FileManager/ProgressDialog2.rc b/CPP/7zip/UI/FileManager/ProgressDialog2.rc
index 92b970f6..2b707451 100755
--- a/CPP/7zip/UI/FileManager/ProgressDialog2.rc
+++ b/CPP/7zip/UI/FileManager/ProgressDialog2.rc
@@ -1,7 +1,7 @@
#include "ProgressDialog2Res.h"
#include "../../GuiCommon.rc"
-#define xSize2 320
+#define xSize2 350
#define ySize2 110
#define xSize (xSize2 + marg + marg)
@@ -20,7 +20,7 @@
#define x1 (marg + x0Size)
#define x1Size 70
-#define x3Size 40
+#define x3Size 60
#define x3 (xSize - marg - x3Size)
#define x2Size 90
diff --git a/CPP/7zip/UI/FileManager/PropertyName.cpp b/CPP/7zip/UI/FileManager/PropertyName.cpp
index cb4edfc2..48090d38 100755
--- a/CPP/7zip/UI/FileManager/PropertyName.cpp
+++ b/CPP/7zip/UI/FileManager/PropertyName.cpp
@@ -3,15 +3,17 @@
#include "StdAfx.h"
#include "Common/IntToString.h"
+
#include "Windows/ResourceString.h"
#include "../../PropID.h"
-#include "resource.h"
-#include "PropertyNameRes.h"
#include "LangUtils.h"
#include "PropertyName.h"
+#include "resource.h"
+#include "PropertyNameRes.h"
+
struct CPropertyIDNamePair
{
PROPID PropID;
@@ -21,60 +23,66 @@ struct CPropertyIDNamePair
static CPropertyIDNamePair kPropertyIDNamePairs[] =
{
- { kpidPath, IDS_PROPERTY_PATH, 0x02000203 },
- { kpidName, IDS_PROPERTY_NAME, 0x02000204 },
- { kpidExtension, IDS_PROPERTY_EXTENSION, 0x02000205 },
- { kpidIsDir, IDS_PROPERTY_IS_FOLDER, 0x02000206},
- { kpidSize, IDS_PROPERTY_SIZE, 0x02000207},
- { kpidPackSize, IDS_PROPERTY_PACKED_SIZE, 0x02000208 },
- { kpidAttrib, IDS_PROPERTY_ATTRIBUTES, 0x02000209 },
- { kpidCTime, IDS_PROPERTY_CTIME, 0x0200020A },
- { kpidATime, IDS_PROPERTY_ATIME, 0x0200020B },
- { kpidMTime, IDS_PROPERTY_MTIME, 0x0200020C },
- { kpidSolid, IDS_PROPERTY_SOLID, 0x0200020D },
- { kpidCommented, IDS_PROPERTY_C0MMENTED, 0x0200020E },
- { kpidEncrypted, IDS_PROPERTY_ENCRYPTED, 0x0200020F },
- { kpidSplitBefore, IDS_PROPERTY_SPLIT_BEFORE, 0x02000210 },
- { kpidSplitAfter, IDS_PROPERTY_SPLIT_AFTER, 0x02000211 },
- { kpidDictionarySize, IDS_PROPERTY_DICTIONARY_SIZE, 0x02000212 },
- { kpidCRC, IDS_PROPERTY_CRC, 0x02000213 },
- { kpidType, IDS_PROPERTY_FILE_TYPE, 0x02000214},
- { kpidIsAnti, IDS_PROPERTY_ANTI, 0x02000215 },
- { kpidMethod, IDS_PROPERTY_METHOD, 0x02000216 },
- { kpidHostOS, IDS_PROPERTY_HOST_OS, 0x02000217 },
- { kpidFileSystem, IDS_PROPERTY_FILE_SYSTEM, 0x02000218},
- { kpidUser, IDS_PROPERTY_USER, 0x02000219},
- { kpidGroup, IDS_PROPERTY_GROUP, 0x0200021A},
- { kpidBlock, IDS_PROPERTY_BLOCK, 0x0200021B },
- { kpidComment, IDS_PROPERTY_COMMENT, 0x0200021C },
- { kpidPosition, IDS_PROPERTY_POSITION, 0x0200021D },
- { kpidPrefix, IDS_PROPERTY_PREFIX, 0x0200021E },
- { kpidNumSubDirs, IDS_PROPERTY_FOLDERS, 0x0200021F },
- { kpidNumSubFiles, IDS_PROPERTY_FILES, 0x02000220 },
- { kpidUnpackVer, IDS_PROPERTY_VERSION, 0x02000221},
- { kpidVolume, IDS_PROPERTY_VOLUME, 0x02000222},
- { kpidIsVolume, IDS_PROPERTY_IS_VOLUME, 0x02000223},
- { kpidOffset, IDS_PROPERTY_OFFSET, 0x02000224},
- { kpidLinks, IDS_PROPERTY_LINKS, 0x02000225},
- { kpidNumBlocks, IDS_PROPERTY_NUM_BLOCKS, 0x02000226},
- { kpidNumVolumes, IDS_PROPERTY_NUM_VOLUMES, 0x02000227},
-
- { kpidBit64, IDS_PROPERTY_BIT64, 0x02000229},
- { kpidBigEndian, IDS_PROPERTY_BIG_ENDIAN, 0x0200022A},
- { kpidCpu, IDS_PROPERTY_CPU, 0x0200022B},
- { kpidPhySize, IDS_PROPERTY_PHY_SIZE, 0x0200022C},
- { kpidHeadersSize, IDS_PROPERTY_HEADERS_SIZE, 0x0200022D},
- { kpidChecksum, IDS_PROPERTY_CHECKSUM, 0x0200022E},
- { kpidCharacts, IDS_PROPERTY_CHARACTS, 0x0200022F},
- { kpidVa, IDS_PROPERTY_VA, 0x02000230},
+ { kpidPath, IDS_PROP_PATH, 0x02000203 },
+ { kpidName, IDS_PROP_NAME, 0x02000204 },
+ { kpidExtension, IDS_PROP_EXTENSION, 0x02000205 },
+ { kpidIsDir, IDS_PROP_IS_FOLDER, 0x02000206},
+ { kpidSize, IDS_PROP_SIZE, 0x02000207},
+ { kpidPackSize, IDS_PROP_PACKED_SIZE, 0x02000208 },
+ { kpidAttrib, IDS_PROP_ATTRIBUTES, 0x02000209 },
+ { kpidCTime, IDS_PROP_CTIME, 0x0200020A },
+ { kpidATime, IDS_PROP_ATIME, 0x0200020B },
+ { kpidMTime, IDS_PROP_MTIME, 0x0200020C },
+ { kpidSolid, IDS_PROP_SOLID, 0x0200020D },
+ { kpidCommented, IDS_PROP_C0MMENTED, 0x0200020E },
+ { kpidEncrypted, IDS_PROP_ENCRYPTED, 0x0200020F },
+ { kpidSplitBefore, IDS_PROP_SPLIT_BEFORE, 0x02000210 },
+ { kpidSplitAfter, IDS_PROP_SPLIT_AFTER, 0x02000211 },
+ { kpidDictionarySize, IDS_PROP_DICTIONARY_SIZE, 0x02000212 },
+ { kpidCRC, IDS_PROP_CRC, 0x02000213 },
+ { kpidType, IDS_PROP_FILE_TYPE, 0x02000214},
+ { kpidIsAnti, IDS_PROP_ANTI, 0x02000215 },
+ { kpidMethod, IDS_PROP_METHOD, 0x02000216 },
+ { kpidHostOS, IDS_PROP_HOST_OS, 0x02000217 },
+ { kpidFileSystem, IDS_PROP_FILE_SYSTEM, 0x02000218},
+ { kpidUser, IDS_PROP_USER, 0x02000219},
+ { kpidGroup, IDS_PROP_GROUP, 0x0200021A},
+ { kpidBlock, IDS_PROP_BLOCK, 0x0200021B },
+ { kpidComment, IDS_PROP_COMMENT, 0x0200021C },
+ { kpidPosition, IDS_PROP_POSITION, 0x0200021D },
+ { kpidPrefix, IDS_PROP_PREFIX, 0x0200021E },
+ { kpidNumSubDirs, IDS_PROP_FOLDERS, 0x0200021F },
+ { kpidNumSubFiles, IDS_PROP_FILES, 0x02000220 },
+ { kpidUnpackVer, IDS_PROP_VERSION, 0x02000221},
+ { kpidVolume, IDS_PROP_VOLUME, 0x02000222},
+ { kpidIsVolume, IDS_PROP_IS_VOLUME, 0x02000223},
+ { kpidOffset, IDS_PROP_OFFSET, 0x02000224},
+ { kpidLinks, IDS_PROP_LINKS, 0x02000225},
+ { kpidNumBlocks, IDS_PROP_NUM_BLOCKS, 0x02000226},
+ { kpidNumVolumes, IDS_PROP_NUM_VOLUMES, 0x02000227},
- { kpidTotalSize, IDS_PROPERTY_TOTAL_SIZE, 0x03031100 },
- { kpidFreeSpace, IDS_PROPERTY_FREE_SPACE, 0x03031101 },
- { kpidClusterSize, IDS_PROPERTY_CLUSTER_SIZE, 0x03031102},
- { kpidVolumeName, IDS_PROPERTY_VOLUME_NAME, 0x03031103 },
+ { kpidBit64, IDS_PROP_BIT64, 0x02000229},
+ { kpidBigEndian, IDS_PROP_BIG_ENDIAN, 0x0200022A},
+ { kpidCpu, IDS_PROP_CPU, 0x0200022B},
+ { kpidPhySize, IDS_PROP_PHY_SIZE, 0x0200022C},
+ { kpidHeadersSize, IDS_PROP_HEADERS_SIZE, 0x0200022D},
+ { kpidChecksum, IDS_PROP_CHECKSUM, 0x0200022E},
+ { kpidCharacts, IDS_PROP_CHARACTS, 0x0200022F},
+ { kpidVa, IDS_PROP_VA, 0x02000230},
+ { kpidId, IDS_PROP_ID, 0x02000231 },
+ { kpidShortName, IDS_PROP_SHORT_NAME, 0x02000232 },
+ { kpidCreatorApp, IDS_PROP_CREATOR_APP, 0x02000233 },
+ { kpidSectorSize, IDS_PROP_SECTOR_SIZE, 0x02000234 },
+ { kpidPosixAttrib, IDS_PROP_POSIX_ATTRIB, 0x02000235 },
+ { kpidLink, IDS_PROP_LINK, 0x02000236 },
+
+ { kpidTotalSize, IDS_PROP_TOTAL_SIZE, 0x03031100 },
+ { kpidFreeSpace, IDS_PROP_FREE_SPACE, 0x03031101 },
+ { kpidClusterSize, IDS_PROP_CLUSTER_SIZE, 0x03031102},
+ { kpidVolumeName, IDS_PROP_VOLUME_NAME, 0x03031103 },
- { kpidLocalName, IDS_PROPERTY_LOCAL_NAME, 0x03031200 },
- { kpidProvider, IDS_PROPERTY_PROVIDER, 0x03031201 }
+ { kpidLocalName, IDS_PROP_LOCAL_NAME, 0x03031200 },
+ { kpidProvider, IDS_PROP_PROVIDER, 0x03031201 }
};
int FindProperty(PROPID propID)
@@ -92,8 +100,8 @@ UString GetNameOfProperty(PROPID propID, const wchar_t *name)
{
if (name)
return name;
- wchar_t s[32];
- ConvertUInt64ToString(propID, s);
+ wchar_t s[16];
+ ConvertUInt32ToString(propID, s);
return s;
}
const CPropertyIDNamePair &pair = kPropertyIDNamePairs[index];
diff --git a/CPP/7zip/UI/FileManager/PropertyName.rc b/CPP/7zip/UI/FileManager/PropertyName.rc
index ad8a9012..576b52cb 100755
--- a/CPP/7zip/UI/FileManager/PropertyName.rc
+++ b/CPP/7zip/UI/FileManager/PropertyName.rc
@@ -4,50 +4,56 @@ LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
STRINGTABLE
BEGIN
- IDS_PROPERTY_PATH "Path"
- IDS_PROPERTY_NAME "Name"
- IDS_PROPERTY_EXTENSION "Extension"
- IDS_PROPERTY_IS_FOLDER "Folder"
- IDS_PROPERTY_SIZE "Size"
- IDS_PROPERTY_PACKED_SIZE "Packed Size"
- IDS_PROPERTY_ATTRIBUTES "Attributes"
- IDS_PROPERTY_CTIME "Created"
- IDS_PROPERTY_ATIME "Accessed"
- IDS_PROPERTY_MTIME "Modified"
- IDS_PROPERTY_SOLID "Solid"
- IDS_PROPERTY_C0MMENTED "Commented"
- IDS_PROPERTY_ENCRYPTED "Encrypted"
- IDS_PROPERTY_DICTIONARY_SIZE "Dictionary Size"
- IDS_PROPERTY_SPLIT_BEFORE "Split Before"
- IDS_PROPERTY_SPLIT_AFTER "Split After"
- IDS_PROPERTY_CRC "CRC"
- IDS_PROPERTY_FILE_TYPE "Type"
- IDS_PROPERTY_ANTI "Anti"
- IDS_PROPERTY_METHOD "Method"
- IDS_PROPERTY_HOST_OS "Host OS"
- IDS_PROPERTY_FILE_SYSTEM "File System"
- IDS_PROPERTY_USER "User"
- IDS_PROPERTY_GROUP "Group"
- IDS_PROPERTY_BLOCK "Block"
- IDS_PROPERTY_COMMENT "Comment"
- IDS_PROPERTY_POSITION "Position"
- IDS_PROPERTY_PREFIX "Path Prefix"
- IDS_PROPERTY_FOLDERS "Folders"
- IDS_PROPERTY_FILES "Files"
- IDS_PROPERTY_VERSION "Version"
- IDS_PROPERTY_VOLUME "Volume"
- IDS_PROPERTY_IS_VOLUME "Multivolume"
- IDS_PROPERTY_OFFSET "Offset"
- IDS_PROPERTY_LINKS "Links"
- IDS_PROPERTY_NUM_BLOCKS "Blocks"
- IDS_PROPERTY_NUM_VOLUMES "Volumes"
+ IDS_PROP_PATH "Path"
+ IDS_PROP_NAME "Name"
+ IDS_PROP_EXTENSION "Extension"
+ IDS_PROP_IS_FOLDER "Folder"
+ IDS_PROP_SIZE "Size"
+ IDS_PROP_PACKED_SIZE "Packed Size"
+ IDS_PROP_ATTRIBUTES "Attributes"
+ IDS_PROP_CTIME "Created"
+ IDS_PROP_ATIME "Accessed"
+ IDS_PROP_MTIME "Modified"
+ IDS_PROP_SOLID "Solid"
+ IDS_PROP_C0MMENTED "Commented"
+ IDS_PROP_ENCRYPTED "Encrypted"
+ IDS_PROP_DICTIONARY_SIZE "Dictionary Size"
+ IDS_PROP_SPLIT_BEFORE "Split Before"
+ IDS_PROP_SPLIT_AFTER "Split After"
+ IDS_PROP_CRC "CRC"
+ IDS_PROP_FILE_TYPE "Type"
+ IDS_PROP_ANTI "Anti"
+ IDS_PROP_METHOD "Method"
+ IDS_PROP_HOST_OS "Host OS"
+ IDS_PROP_FILE_SYSTEM "File System"
+ IDS_PROP_USER "User"
+ IDS_PROP_GROUP "Group"
+ IDS_PROP_BLOCK "Block"
+ IDS_PROP_COMMENT "Comment"
+ IDS_PROP_POSITION "Position"
+ IDS_PROP_PREFIX "Path Prefix"
+ IDS_PROP_FOLDERS "Folders"
+ IDS_PROP_FILES "Files"
+ IDS_PROP_VERSION "Version"
+ IDS_PROP_VOLUME "Volume"
+ IDS_PROP_IS_VOLUME "Multivolume"
+ IDS_PROP_OFFSET "Offset"
+ IDS_PROP_LINKS "Links"
+ IDS_PROP_NUM_BLOCKS "Blocks"
+ IDS_PROP_NUM_VOLUMES "Volumes"
- IDS_PROPERTY_BIT64 "64-bit"
- IDS_PROPERTY_BIG_ENDIAN "Big-endian"
- IDS_PROPERTY_CPU "CPU"
- IDS_PROPERTY_PHY_SIZE "Physical Size"
- IDS_PROPERTY_HEADERS_SIZE "Headers Size"
- IDS_PROPERTY_CHECKSUM "Checksum"
- IDS_PROPERTY_CHARACTS "Characteristics"
- IDS_PROPERTY_VA "Va"
+ IDS_PROP_BIT64 "64-bit"
+ IDS_PROP_BIG_ENDIAN "Big-endian"
+ IDS_PROP_CPU "CPU"
+ IDS_PROP_PHY_SIZE "Physical Size"
+ IDS_PROP_HEADERS_SIZE "Headers Size"
+ IDS_PROP_CHECKSUM "Checksum"
+ IDS_PROP_CHARACTS "Characteristics"
+ IDS_PROP_VA "Virtual Address"
+ IDS_PROP_ID "ID"
+ IDS_PROP_SHORT_NAME "Short Name"
+ IDS_PROP_CREATOR_APP "Creator Application"
+ IDS_PROP_SECTOR_SIZE "Sector Size"
+ IDS_PROP_POSIX_ATTRIB "Mode"
+ IDS_PROP_LINK "Link"
END
diff --git a/CPP/7zip/UI/FileManager/PropertyNameRes.h b/CPP/7zip/UI/FileManager/PropertyNameRes.h
index 74d535ac..00458a24 100755
--- a/CPP/7zip/UI/FileManager/PropertyNameRes.h
+++ b/CPP/7zip/UI/FileManager/PropertyNameRes.h
@@ -1,46 +1,52 @@
-#define IDS_PROPERTY_PATH 3
-#define IDS_PROPERTY_NAME 4
-#define IDS_PROPERTY_EXTENSION 5
-#define IDS_PROPERTY_IS_FOLDER 6
-#define IDS_PROPERTY_SIZE 7
-#define IDS_PROPERTY_PACKED_SIZE 8
-#define IDS_PROPERTY_ATTRIBUTES 9
-#define IDS_PROPERTY_CTIME 10
-#define IDS_PROPERTY_ATIME 11
-#define IDS_PROPERTY_MTIME 12
-#define IDS_PROPERTY_SOLID 13
-#define IDS_PROPERTY_C0MMENTED 14
-#define IDS_PROPERTY_ENCRYPTED 15
-#define IDS_PROPERTY_DICTIONARY_SIZE 16
-#define IDS_PROPERTY_SPLIT_BEFORE 17
-#define IDS_PROPERTY_SPLIT_AFTER 18
-#define IDS_PROPERTY_CRC 19
-#define IDS_PROPERTY_FILE_TYPE 20
-#define IDS_PROPERTY_ANTI 21
-#define IDS_PROPERTY_METHOD 22
-#define IDS_PROPERTY_HOST_OS 23
-#define IDS_PROPERTY_FILE_SYSTEM 24
-#define IDS_PROPERTY_USER 25
-#define IDS_PROPERTY_GROUP 26
-#define IDS_PROPERTY_BLOCK 27
-#define IDS_PROPERTY_COMMENT 28
-#define IDS_PROPERTY_POSITION 29
-#define IDS_PROPERTY_PREFIX 30
-#define IDS_PROPERTY_FOLDERS 31
-#define IDS_PROPERTY_FILES 32
-#define IDS_PROPERTY_VERSION 33
-#define IDS_PROPERTY_VOLUME 34
-#define IDS_PROPERTY_IS_VOLUME 35
-#define IDS_PROPERTY_OFFSET 36
-#define IDS_PROPERTY_LINKS 37
-#define IDS_PROPERTY_NUM_BLOCKS 38
-#define IDS_PROPERTY_NUM_VOLUMES 39
+#define IDS_PROP_PATH 3
+#define IDS_PROP_NAME 4
+#define IDS_PROP_EXTENSION 5
+#define IDS_PROP_IS_FOLDER 6
+#define IDS_PROP_SIZE 7
+#define IDS_PROP_PACKED_SIZE 8
+#define IDS_PROP_ATTRIBUTES 9
+#define IDS_PROP_CTIME 10
+#define IDS_PROP_ATIME 11
+#define IDS_PROP_MTIME 12
+#define IDS_PROP_SOLID 13
+#define IDS_PROP_C0MMENTED 14
+#define IDS_PROP_ENCRYPTED 15
+#define IDS_PROP_DICTIONARY_SIZE 16
+#define IDS_PROP_SPLIT_BEFORE 17
+#define IDS_PROP_SPLIT_AFTER 18
+#define IDS_PROP_CRC 19
+#define IDS_PROP_FILE_TYPE 20
+#define IDS_PROP_ANTI 21
+#define IDS_PROP_METHOD 22
+#define IDS_PROP_HOST_OS 23
+#define IDS_PROP_FILE_SYSTEM 24
+#define IDS_PROP_USER 25
+#define IDS_PROP_GROUP 26
+#define IDS_PROP_BLOCK 27
+#define IDS_PROP_COMMENT 28
+#define IDS_PROP_POSITION 29
+#define IDS_PROP_PREFIX 30
+#define IDS_PROP_FOLDERS 31
+#define IDS_PROP_FILES 32
+#define IDS_PROP_VERSION 33
+#define IDS_PROP_VOLUME 34
+#define IDS_PROP_IS_VOLUME 35
+#define IDS_PROP_OFFSET 36
+#define IDS_PROP_LINKS 37
+#define IDS_PROP_NUM_BLOCKS 38
+#define IDS_PROP_NUM_VOLUMES 39
-#define IDS_PROPERTY_BIT64 41
-#define IDS_PROPERTY_BIG_ENDIAN 42
-#define IDS_PROPERTY_CPU 43
-#define IDS_PROPERTY_PHY_SIZE 44
-#define IDS_PROPERTY_HEADERS_SIZE 45
-#define IDS_PROPERTY_CHECKSUM 46
-#define IDS_PROPERTY_CHARACTS 47
-#define IDS_PROPERTY_VA 48
+#define IDS_PROP_BIT64 41
+#define IDS_PROP_BIG_ENDIAN 42
+#define IDS_PROP_CPU 43
+#define IDS_PROP_PHY_SIZE 44
+#define IDS_PROP_HEADERS_SIZE 45
+#define IDS_PROP_CHECKSUM 46
+#define IDS_PROP_CHARACTS 47
+#define IDS_PROP_VA 48
+#define IDS_PROP_ID 49
+#define IDS_PROP_SHORT_NAME 50
+#define IDS_PROP_CREATOR_APP 51
+#define IDS_PROP_SECTOR_SIZE 52
+#define IDS_PROP_POSIX_ATTRIB 53
+#define IDS_PROP_LINK 54
diff --git a/CPP/7zip/UI/FileManager/RegistryAssociations.cpp b/CPP/7zip/UI/FileManager/RegistryAssociations.cpp
index 8c6e6ae8..d4fbfe13 100755
--- a/CPP/7zip/UI/FileManager/RegistryAssociations.cpp
+++ b/CPP/7zip/UI/FileManager/RegistryAssociations.cpp
@@ -4,21 +4,18 @@
#include "RegistryAssociations.h"
-#include "Common/StringConvert.h"
#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
#include "Common/StringToInt.h"
-#include "Windows/Synchronization.h"
#include "Windows/Registry.h"
-
-#include "Windows/FileName.h"
+#include "Windows/Synchronization.h"
#include "StringUtils.h"
using namespace NWindows;
using namespace NRegistry;
-
namespace NRegistryAssociations {
static NSynchronization::CCriticalSection g_CriticalSection;
@@ -218,8 +215,8 @@ void AddShellExtensionInfo(const CSysString &extension,
if (iconIndex >= 0)
{
iconPathFull += L",";
- wchar_t s[32];
- ConvertUInt64ToString((UInt64)iconIndex, s);
+ wchar_t s[16];
+ ConvertUInt32ToString(iconIndex, s);
iconPathFull += s;
}
iconKey.SetValue(NULL, iconPathFull);
diff --git a/CPP/7zip/UI/FileManager/RegistryUtils.cpp b/CPP/7zip/UI/FileManager/RegistryUtils.cpp
index ed118457..bd1248a2 100755
--- a/CPP/7zip/UI/FileManager/RegistryUtils.cpp
+++ b/CPP/7zip/UI/FileManager/RegistryUtils.cpp
@@ -2,10 +2,12 @@
#include "StdAfx.h"
-#include "RegistryUtils.h"
#include "Common/IntToString.h"
+
#include "Windows/Registry.h"
+#include "RegistryUtils.h"
+
using namespace NWindows;
using namespace NRegistry;
@@ -17,6 +19,7 @@ static const TCHAR *kCU_FMPath = REG_PATH_7Z TEXT(STRING_PATH_SEPARATOR) TEXT("F
static const WCHAR *kLangValueName = L"Lang";
static const WCHAR *kEditor = L"Editor";
+static const WCHAR *kDiff = L"Diff";
static const TCHAR *kShowDots = TEXT("ShowDots");
static const TCHAR *kShowRealFileIcons = TEXT("ShowRealFileIcons");
static const TCHAR *kShowSystemMenu = TEXT("ShowSystemMenu");
@@ -31,35 +34,29 @@ static const TCHAR *kLargePagesEnable = TEXT("LargePages");
static const TCHAR *kFlatViewName = TEXT("FlatViewArc");
-void SaveRegLang(const UString &langFile)
+static void SaveCuString(LPCTSTR keyPath, LPCWSTR valuePath, LPCWSTR value)
{
CKey key;
- key.Create(HKEY_CURRENT_USER, kCUBasePath);
- key.SetValue(kLangValueName, langFile);
+ key.Create(HKEY_CURRENT_USER, keyPath);
+ key.SetValue(valuePath, value);
}
-void ReadRegLang(UString &langFile)
+static void ReadCuString(LPCTSTR keyPath, LPCWSTR valuePath, UString &res)
{
- langFile.Empty();
+ res.Empty();
CKey key;
- if (key.Open(HKEY_CURRENT_USER, kCUBasePath, KEY_READ) == ERROR_SUCCESS)
- key.QueryValue(kLangValueName, langFile);
+ if (key.Open(HKEY_CURRENT_USER, keyPath, KEY_READ) == ERROR_SUCCESS)
+ key.QueryValue(valuePath, res);
}
-void SaveRegEditor(const UString &editorPath)
-{
- CKey key;
- key.Create(HKEY_CURRENT_USER, kCU_FMPath);
- key.SetValue(kEditor, editorPath);
-}
+void SaveRegLang(const UString &path) { SaveCuString(kCUBasePath, kLangValueName, path); }
+void ReadRegLang(UString &path) { ReadCuString(kCUBasePath, kLangValueName, path); }
-void ReadRegEditor(UString &editorPath)
-{
- editorPath.Empty();
- CKey key;
- if (key.Open(HKEY_CURRENT_USER, kCU_FMPath, KEY_READ) == ERROR_SUCCESS)
- key.QueryValue(kEditor, editorPath);
-}
+void SaveRegEditor(const UString &path) { SaveCuString(kCU_FMPath, kEditor, path); }
+void ReadRegEditor(UString &path) { ReadCuString(kCU_FMPath, kEditor, path); }
+
+void SaveRegDiff(const UString &path) { SaveCuString(kCU_FMPath, kDiff, path); }
+void ReadRegDiff(UString &path) { ReadCuString(kCU_FMPath, kDiff, path); }
static void Save7ZipOption(const TCHAR *value, bool enabled)
{
@@ -154,8 +151,8 @@ bool ReadLockMemoryEnable() { return Read7ZipOption(kLargePagesEnable, false); }
static CSysString GetFlatViewName(UInt32 panelIndex)
{
- TCHAR panelString[32];
- ConvertUInt64ToString(panelIndex, panelString);
+ TCHAR panelString[16];
+ ConvertUInt32ToString(panelIndex, panelString);
return (CSysString)kFlatViewName + panelString;
}
diff --git a/CPP/7zip/UI/FileManager/RegistryUtils.h b/CPP/7zip/UI/FileManager/RegistryUtils.h
index 9b9c91cf..5469f401 100755
--- a/CPP/7zip/UI/FileManager/RegistryUtils.h
+++ b/CPP/7zip/UI/FileManager/RegistryUtils.h
@@ -1,15 +1,18 @@
// RegistryUtils.h
-#include "Common/StringConvert.h"
+#ifndef __REGISTRY_UTILS_H
+#define __REGISTRY_UTILS_H
-#ifndef __REGISTRYUTILS_H
-#define __REGISTRYUTILS_H
+#include "Common/MyString.h"
-void SaveRegLang(const UString &langFile);
-void ReadRegLang(UString &langFile);
+void SaveRegLang(const UString &path);
+void ReadRegLang(UString &path);
-void SaveRegEditor(const UString &editorPath);
-void ReadRegEditor(UString &editorPath);
+void SaveRegEditor(const UString &path);
+void ReadRegEditor(UString &path);
+
+void SaveRegDiff(const UString &path);
+void ReadRegDiff(UString &path);
void SaveShowDots(bool showDots);
bool ReadShowDots();
diff --git a/CPP/7zip/UI/FileManager/RootFolder.cpp b/CPP/7zip/UI/FileManager/RootFolder.cpp
index 1cb71e5f..ea6f5080 100755
--- a/CPP/7zip/UI/FileManager/RootFolder.cpp
+++ b/CPP/7zip/UI/FileManager/RootFolder.cpp
@@ -2,32 +2,28 @@
#include "StdAfx.h"
-#include "resource.h"
+#include "Common/StringConvert.h"
-#include "RootFolder.h"
+#include "Windows/PropVariant.h"
-#include "Common/StringConvert.h"
#include "../../PropID.h"
-#include "Windows/Defs.h"
-#include "Windows/PropVariant.h"
#include "FSDrives.h"
-#include "PhysDriveFolder.h"
+#include "FSFolder.h"
+#include "LangUtils.h"
#include "NetFolder.h"
+#include "RootFolder.h"
#include "SysIconUtils.h"
-#include "LangUtils.h"
-using namespace NWindows;
+#include "resource.h"
+using namespace NWindows;
-static const STATPROPSTG kProperties[] =
+static const STATPROPSTG kProps[] =
{
{ NULL, kpidName, VT_BSTR}
};
-// static const wchar_t *kMyComputerTitle = L"Computer";
-// static const wchar_t *kMyNetworkTitle = L"Network";
-
UString RootFolder_GetName_Computer(int &iconIndex)
{
iconIndex = GetIconIndexForCSIDL(CSIDL_DRIVES);
@@ -49,12 +45,17 @@ UString RootFolder_GetName_Documents(int &iconIndex)
const int ROOT_INDEX_COMPUTER = 0;
const int ROOT_INDEX_DOCUMENTS = 1;
const int ROOT_INDEX_NETWORK = 2;
+const int ROOT_INDEX_VOLUMES = 3;
+
+static const wchar_t *kVolPrefix = L"\\\\.\\";
void CRootFolder::Init()
{
_names[ROOT_INDEX_COMPUTER] = RootFolder_GetName_Computer(_iconIndices[ROOT_INDEX_COMPUTER]);
_names[ROOT_INDEX_DOCUMENTS] = RootFolder_GetName_Documents(_iconIndices[ROOT_INDEX_DOCUMENTS]);
_names[ROOT_INDEX_NETWORK] = RootFolder_GetName_Network(_iconIndices[ROOT_INDEX_NETWORK]);
+ _names[ROOT_INDEX_VOLUMES] = kVolPrefix;
+ _iconIndices[ROOT_INDEX_VOLUMES] = GetIconIndexForCSIDL(CSIDL_DRIVES);
};
STDMETHODIMP CRootFolder::LoadItems()
@@ -109,19 +110,19 @@ UString GetMyDocsPath()
STDMETHODIMP CRootFolder::BindToFolder(UInt32 index, IFolderFolder **resultFolder)
{
- if (index == ROOT_INDEX_COMPUTER)
+ *resultFolder = NULL;
+ CMyComPtr<IFolderFolder> subFolder;
+ if (index == ROOT_INDEX_COMPUTER || index == ROOT_INDEX_VOLUMES)
{
CFSDrives *fsDrivesSpec = new CFSDrives;
- CMyComPtr<IFolderFolder> subFolder = fsDrivesSpec;
- fsDrivesSpec->Init();
- *resultFolder = subFolder.Detach();
+ subFolder = fsDrivesSpec;
+ fsDrivesSpec->Init(index == ROOT_INDEX_VOLUMES);
}
else if (index == ROOT_INDEX_NETWORK)
{
CNetFolder *netFolderSpec = new CNetFolder;
- CMyComPtr<IFolderFolder> subFolder = netFolderSpec;
+ subFolder = netFolderSpec;
netFolderSpec->Init(0, 0, _names[ROOT_INDEX_NETWORK] + WCHAR_PATH_SEPARATOR);
- *resultFolder = subFolder.Detach();
}
else if (index == ROOT_INDEX_DOCUMENTS)
{
@@ -129,13 +130,13 @@ STDMETHODIMP CRootFolder::BindToFolder(UInt32 index, IFolderFolder **resultFolde
if (!s.IsEmpty())
{
NFsFolder::CFSFolder *fsFolderSpec = new NFsFolder::CFSFolder;
- CMyComPtr<IFolderFolder> subFolder = fsFolderSpec;
+ subFolder = fsFolderSpec;
RINOK(fsFolderSpec->Init(s, NULL));
- *resultFolder = subFolder.Detach();
}
}
else
return E_INVALIDARG;
+ *resultFolder = subFolder.Detach();
return S_OK;
}
@@ -178,11 +179,11 @@ STDMETHODIMP CRootFolder::BindToFolder(const wchar_t *name, IFolderFolder **resu
CMyComPtr<IFolderFolder> subFolder;
- if (name2.Left(4) == L"\\\\.\\")
+ if (name2.Left(4) == kVolPrefix)
{
- CPhysDriveFolder *folderSpec = new CPhysDriveFolder;
+ CFSDrives *folderSpec = new CFSDrives;
subFolder = folderSpec;
- RINOK(folderSpec->Init(name2.Mid(4, 2)));
+ folderSpec->Init(true);
}
else
{
@@ -212,23 +213,7 @@ STDMETHODIMP CRootFolder::BindToParentFolder(IFolderFolder **resultFolder)
return S_OK;
}
-STDMETHODIMP CRootFolder::GetNumberOfProperties(UInt32 *numProperties)
-{
- *numProperties = sizeof(kProperties) / sizeof(kProperties[0]);
- return S_OK;
-}
-
-STDMETHODIMP CRootFolder::GetPropertyInfo(UInt32 index,
- BSTR *name, PROPID *propID, VARTYPE *varType)
-{
- if (index >= sizeof(kProperties) / sizeof(kProperties[0]))
- return E_INVALIDARG;
- const STATPROPSTG &prop = kProperties[index];
- *propID = prop.propid;
- *varType = prop.vt;
- *name = 0;
- return S_OK;
-}
+IMP_IFolderFolder_Props(CRootFolder)
STDMETHODIMP CRootFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
{
@@ -242,7 +227,7 @@ STDMETHODIMP CRootFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
return S_OK;
}
-STDMETHODIMP CRootFolder::GetSystemIconIndex(UInt32 index, INT32 *iconIndex)
+STDMETHODIMP CRootFolder::GetSystemIconIndex(UInt32 index, Int32 *iconIndex)
{
*iconIndex = _iconIndices[index];
return S_OK;
diff --git a/CPP/7zip/UI/FileManager/RootFolder.h b/CPP/7zip/UI/FileManager/RootFolder.h
index f17a0783..9f08e601 100755
--- a/CPP/7zip/UI/FileManager/RootFolder.h
+++ b/CPP/7zip/UI/FileManager/RootFolder.h
@@ -1,34 +1,27 @@
// RootFolder.h
-#ifndef __ROOTFOLDER_H
-#define __ROOTFOLDER_H
+#ifndef __ROOT_FOLDER_H
+#define __ROOT_FOLDER_H
#include "Common/MyString.h"
-#include "Windows/PropVariant.h"
+#include "IFolder.h"
-#include "FSFolder.h"
-
-const int kNumRootFolderItems = 3;
+const int kNumRootFolderItems = 4;
class CRootFolder:
public IFolderFolder,
public IFolderGetSystemIconIndex,
public CMyUnknownImp
{
-public:
- MY_UNKNOWN_IMP1(
- IFolderGetSystemIconIndex
- )
+ UString _names[kNumRootFolderItems];
+ int _iconIndices[kNumRootFolderItems];
+public:
+ MY_UNKNOWN_IMP1(IFolderGetSystemIconIndex)
INTERFACE_FolderFolder(;)
-
- STDMETHOD(GetSystemIconIndex)(UInt32 index, INT32 *iconIndex);
-
+ STDMETHOD(GetSystemIconIndex)(UInt32 index, Int32 *iconIndex);
void Init();
-private:
- UString _names[kNumRootFolderItems];
- int _iconIndices[kNumRootFolderItems];
};
#endif
diff --git a/CPP/7zip/UI/FileManager/SysIconUtils.cpp b/CPP/7zip/UI/FileManager/SysIconUtils.cpp
index 5af6f850..3e5de7aa 100755
--- a/CPP/7zip/UI/FileManager/SysIconUtils.cpp
+++ b/CPP/7zip/UI/FileManager/SysIconUtils.cpp
@@ -131,10 +131,7 @@ int CExtToIconMap::GetIconIndex(UINT32 attributes, const UString &fileNameSpec,
{
fileName = L"__File__";
if (_noExtIconIndex < 0)
- {
- int iconIndexTemp;
- GetRealIconIndex(fileName, attributes, iconIndexTemp, _noExtTypeName);
- }
+ GetRealIconIndex(fileName, attributes, _noExtIconIndex, _noExtTypeName);
typeName = _noExtTypeName;
return _noExtIconIndex;
}
diff --git a/CPP/7zip/UI/FileManager/SystemPage.cpp b/CPP/7zip/UI/FileManager/SystemPage.cpp
index f8605ea8..1cd7ce15 100755
--- a/CPP/7zip/UI/FileManager/SystemPage.cpp
+++ b/CPP/7zip/UI/FileManager/SystemPage.cpp
@@ -52,7 +52,7 @@ bool CSystemPage::OnInit()
_listViewExt.SetExtendedListViewStyle(newFlags, newFlags);
_listViewPlugins.SetExtendedListViewStyle(newFlags, newFlags);
- _listViewExt.InsertColumn(0, LangString(IDS_PROPERTY_EXTENSION, 0x02000205), 70);
+ _listViewExt.InsertColumn(0, LangString(IDS_PROP_EXTENSION, 0x02000205), 70);
const UString s = LangString(IDS_PLUGIN, 0x03010310);
_listViewExt.InsertColumn(1, s, 70);
diff --git a/CPP/7zip/UI/FileManager/SystemPage.rc b/CPP/7zip/UI/FileManager/SystemPage.rc
index 1cf9405f..9b4e808d 100755
--- a/CPP/7zip/UI/FileManager/SystemPage.rc
+++ b/CPP/7zip/UI/FileManager/SystemPage.rc
@@ -1,12 +1,11 @@
#include "SystemPageRes.h"
#include "../../GuiCommon.rc"
-#define xSize2 238
-#define ySize2 214
+#define xSize2 196
+#define ySize2 200
#define xSize (xSize2 + marg + marg)
#define ySize (ySize2 + marg + marg)
-#define gSpace 30
-#define g0Size 160
+#define g0Size xSize2
#define gYSize (ySize2 - 20 - bYSize)
diff --git a/CPP/7zip/UI/FileManager/TextPairs.cpp b/CPP/7zip/UI/FileManager/TextPairs.cpp
index 74df1c62..cc57c0d5 100755
--- a/CPP/7zip/UI/FileManager/TextPairs.cpp
+++ b/CPP/7zip/UI/FileManager/TextPairs.cpp
@@ -1,28 +1,20 @@
-// Common/TextPairs.cpp
+// TextPairs.cpp
#include "StdAfx.h"
#include "TextPairs.h"
-#include "Common/Defs.h"
-#include "Common/UTFConvert.h"
-
static const wchar_t kNewLineChar = '\n';
+static const wchar_t kQuoteChar = '\"';
-static const wchar_t kSpaceChar = ' ';
-static const wchar_t kTabChar = '\t';
-
-static const wchar_t kQuoteChar = '\"';
-static const wchar_t kEndOfLine = '\0';
-
-static const wchar_t kBOM = wchar_t(0xFEFF);
+static const wchar_t kBOM = (wchar_t)0xFEFF;
static bool IsSeparatorChar(wchar_t c)
{
- return (c == kSpaceChar || c == kTabChar);
+ return (c == ' ' || c == '\t');
}
-void RemoveCr(UString &s)
+static void RemoveCr(UString &s)
{
s.Replace(L"\x0D", L"");
}
@@ -34,7 +26,7 @@ static UString GetIDString(const wchar_t *srcString, int &finishPos)
for (finishPos = 0;;)
{
wchar_t c = srcString[finishPos];
- if (c == kEndOfLine)
+ if (c == 0)
break;
finishPos++;
bool isSeparatorChar = IsSeparatorChar(c);
@@ -57,7 +49,7 @@ static UString GetValueString(const wchar_t *srcString, int &finishPos)
for (finishPos = 0;;)
{
wchar_t c = srcString[finishPos];
- if (c == kEndOfLine)
+ if (c == 0)
break;
finishPos++;
if (c == kNewLineChar)
@@ -99,42 +91,22 @@ static bool GetTextPairs(const UString &srcString, CObjectVector<CTextPair> &pai
return true;
}
-int FindItem(const CObjectVector<CTextPair> &pairs, const UString &id)
-{
- for (int i = 0; i < pairs.Size(); i++)
- if (pairs[i].ID.CompareNoCase(id) == 0)
- return i;
- return -1;
-}
-
-UString GetTextConfigValue(const CObjectVector<CTextPair> &pairs, const UString &id)
-{
- int index = FindItem(pairs, id);
- if (index < 0)
- return UString();
- return pairs[index].Value;
-}
-
static int ComparePairIDs(const UString &s1, const UString &s2)
{ return s1.CompareNoCase(s2); }
static int ComparePairItems(const CTextPair &p1, const CTextPair &p2)
{ return ComparePairIDs(p1.ID, p2.ID); }
-// typedef void* MY_PVOID;
-
-// static int ComparePairItems(const MY_PVOID *a1, const MY_PVOID *a2, void *param)
static int ComparePairItems(void *const *a1, void *const *a2, void * /* param */)
{ return ComparePairItems(**(const CTextPair **)a1, **(const CTextPair **)a2); }
-void CPairsStorage::Sort()
- { Pairs.Sort(ComparePairItems, 0); }
+void CPairsStorage::Sort() { Pairs.Sort(ComparePairItems, 0); }
int CPairsStorage::FindID(const UString &id, int &insertPos)
{
int left = 0, right = Pairs.Size();
while (left != right)
{
- UINT32 mid = (left + right) / 2;
+ int mid = (left + right) / 2;
int compResult = ComparePairIDs(id, Pairs[mid].ID);
if (compResult == 0)
return mid;
diff --git a/CPP/7zip/UI/FileManager/TextPairs.h b/CPP/7zip/UI/FileManager/TextPairs.h
index b75d9c72..2670e030 100755
--- a/CPP/7zip/UI/FileManager/TextPairs.h
+++ b/CPP/7zip/UI/FileManager/TextPairs.h
@@ -1,7 +1,7 @@
-// Common/TextPairs.h
+// TextPairs.h
-#ifndef __COMMON_TEXTPAIRS_H
-#define __COMMON_TEXTPAIRS_H
+#ifndef __FM_TEXT_PAIRS_H
+#define __FM_TEXT_PAIRS_H
#include "Common/MyString.h"
diff --git a/CPP/7zip/UI/FileManager/UpdateCallback100.cpp b/CPP/7zip/UI/FileManager/UpdateCallback100.cpp
index e23c7d34..3701d2bb 100755
--- a/CPP/7zip/UI/FileManager/UpdateCallback100.cpp
+++ b/CPP/7zip/UI/FileManager/UpdateCallback100.cpp
@@ -1,17 +1,10 @@
-// UpdateCallback.h
+// UpdateCallback100.cpp
#include "StdAfx.h"
-#include "Common/StringConvert.h"
-
-#include "UpdateCallback100.h"
-// #include "Windows/ProcessMessages.h"
-// #include "Resource/PasswordDialog/PasswordDialog.h"
#include "MessagesDialog.h"
-
-#include "Common/Defs.h"
-
-using namespace NWindows;
+#include "PasswordDialog.h"
+#include "UpdateCallback100.h"
CUpdateCallback100Imp::~CUpdateCallback100Imp()
{
@@ -81,19 +74,10 @@ STDMETHODIMP CUpdateCallback100Imp::UpdateErrorMessage(const wchar_t *message)
STDMETHODIMP CUpdateCallback100Imp::CryptoGetTextPassword2(Int32 *passwordIsDefined, BSTR *password)
{
+ *password = NULL;
*passwordIsDefined = BoolToInt(_passwordIsDefined);
if (!_passwordIsDefined)
- {
return S_OK;
- /*
- CPasswordDialog dialog;
- if (dialog.Create(_parentWindow) == IDCANCEL)
- return E_ABORT;
- _password = dialog._password;
- _passwordIsDefined = true;
- */
- }
- *passwordIsDefined = BoolToInt(_passwordIsDefined);
return StringToBstr(_password, password);
}
@@ -109,7 +93,14 @@ STDMETHODIMP CUpdateCallback100Imp::SetCompleted(const UInt64 * /* files */, con
STDMETHODIMP CUpdateCallback100Imp::CryptoGetTextPassword(BSTR *password)
{
+ *password = NULL;
if (!_passwordIsDefined)
- return S_FALSE;
+ {
+ CPasswordDialog dialog;
+ if (dialog.Create(_parentWindow) == IDCANCEL)
+ return E_ABORT;
+ _password = dialog.Password;
+ _passwordIsDefined = true;
+ }
return StringToBstr(_password, password);
}
diff --git a/CPP/7zip/UI/FileManager/ViewSettings.cpp b/CPP/7zip/UI/FileManager/ViewSettings.cpp
index 6c611dad..0f98c217 100755
--- a/CPP/7zip/UI/FileManager/ViewSettings.cpp
+++ b/CPP/7zip/UI/FileManager/ViewSettings.cpp
@@ -297,8 +297,8 @@ UInt32 ReadToolbarsMask()
static UString GetPanelPathName(UInt32 panelIndex)
{
- WCHAR panelString[32];
- ConvertUInt64ToString(panelIndex, panelString);
+ WCHAR panelString[16];
+ ConvertUInt32ToString(panelIndex, panelString);
return UString(kPanelPathValueName) + panelString;
}
diff --git a/CPP/7zip/UI/FileManager/makefile b/CPP/7zip/UI/FileManager/makefile
index 86bdd85f..fea2d39a 100755
--- a/CPP/7zip/UI/FileManager/makefile
+++ b/CPP/7zip/UI/FileManager/makefile
@@ -5,6 +5,7 @@ CFLAGS = $(CFLAGS) -I ../../../ \
-DWIN_LONG_PATH \
-DNEW_FOLDER_INTERFACE \
-DEXTERNAL_CODECS \
+ -DSUPPORT_DEVICE_FILE \
FM_OBJS = \
$O\App.obj \
@@ -38,7 +39,6 @@ FM_OBJS = \
$O\PanelSelect.obj \
$O\PanelSort.obj \
$O\PanelSplitFile.obj \
- $O\PhysDriveFolder.obj \
$O\ProgramLocation.obj \
$O\PropertyName.obj \
$O\RegistryAssociations.obj \
@@ -85,7 +85,6 @@ WIN_OBJS = \
$O\CommonDialog.obj \
$O\DLL.obj \
$O\Error.obj \
- $O\FileDevice.obj \
$O\FileDir.obj \
$O\FileFind.obj \
$O\FileIO.obj \
@@ -138,6 +137,9 @@ UI_COMMON_OBJS = \
$O\WorkDir.obj \
$O\ZipRegistry.obj \
+AR_COMMON_OBJS = \
+ $O\OutStreamWithCRC.obj \
+
AGENT_OBJS = \
$O\Agent.obj \
$O\AgentOut.obj \
@@ -163,6 +165,7 @@ OBJS = \
$(WIN_CTRL_OBJS) \
$(7ZIP_COMMON_OBJS) \
$(UI_COMMON_OBJS) \
+ $(AR_COMMON_OBJS) \
$(AGENT_OBJS) \
$O\CopyCoder.obj \
$(CRC_OBJS) \
@@ -183,6 +186,8 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(UI_COMMON_OBJS): ../Common/$(*B).cpp
$(COMPL)
+$(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
+ $(COMPL)
$(AGENT_OBJS): ../Agent/$(*B).cpp
$(COMPL)
diff --git a/CPP/7zip/UI/FileManager/resource.h b/CPP/7zip/UI/FileManager/resource.h
index edd351b6..72121c89 100755
--- a/CPP/7zip/UI/FileManager/resource.h
+++ b/CPP/7zip/UI/FileManager/resource.h
@@ -17,6 +17,7 @@
#define IDM_FILE_PROPERTIES 240
#define IDM_FILE_COMMENT 241
#define IDM_FILE_CRC 242
+#define IDM_FILE_DIFF 243
#define IDM_CREATE_FOLDER 250
#define IDM_CREATE_FILE 251
#define IDM_EDIT_CUT 320
@@ -128,12 +129,12 @@
#define IDS_BUTTON_MOVE 2421
#define IDS_BUTTON_DELETE 2422
#define IDS_BUTTON_INFO 2423
-#define IDS_PROPERTY_TOTAL_SIZE 3100
-#define IDS_PROPERTY_FREE_SPACE 3101
-#define IDS_PROPERTY_CLUSTER_SIZE 3102
-#define IDS_PROPERTY_VOLUME_NAME 3103
-#define IDS_PROPERTY_LOCAL_NAME 3200
-#define IDS_PROPERTY_PROVIDER 3201
+#define IDS_PROP_TOTAL_SIZE 3100
+#define IDS_PROP_FREE_SPACE 3101
+#define IDS_PROP_CLUSTER_SIZE 3102
+#define IDS_PROP_VOLUME_NAME 3103
+#define IDS_PROP_LOCAL_NAME 3200
+#define IDS_PROP_PROVIDER 3201
#define IDS_OPTIONS 4000
#define IDS_COMMENT 4001
#define IDS_COMMENT2 4002
diff --git a/CPP/7zip/UI/FileManager/resource.rc b/CPP/7zip/UI/FileManager/resource.rc
index 3ec3bb32..cdfed0b6 100755
--- a/CPP/7zip/UI/FileManager/resource.rc
+++ b/CPP/7zip/UI/FileManager/resource.rc
@@ -34,6 +34,7 @@ BEGIN
MENUITEM "P&roperties\tAlt+Enter", IDM_FILE_PROPERTIES
MENUITEM "Comme&nt\tCtrl+Z", IDM_FILE_COMMENT
MENUITEM "Calculate checksum", IDM_FILE_CRC
+ MENUITEM "Di&ff", IDM_FILE_DIFF
MENUITEM SEPARATOR
MENUITEM "Create Folder\tF7", IDM_CREATE_FOLDER
MENUITEM "Create File\tCtrl+N", IDM_CREATE_FILE
@@ -190,12 +191,12 @@ BEGIN
IDS_FOLDERS_COLON "Folders:"
IDS_SIZE_COLON "Size:"
- IDS_PROPERTY_TOTAL_SIZE "Total Size"
- IDS_PROPERTY_FREE_SPACE "Free Space"
- IDS_PROPERTY_CLUSTER_SIZE "Cluster Size"
- IDS_PROPERTY_VOLUME_NAME "Label"
- IDS_PROPERTY_LOCAL_NAME "Local Name"
- IDS_PROPERTY_PROVIDER "Provider"
+ IDS_PROP_TOTAL_SIZE "Total Size"
+ IDS_PROP_FREE_SPACE "Free Space"
+ IDS_PROP_CLUSTER_SIZE "Cluster Size"
+ IDS_PROP_VOLUME_NAME "Label"
+ IDS_PROP_LOCAL_NAME "Local Name"
+ IDS_PROP_PROVIDER "Provider"
IDS_OPTIONS "Options"
IDS_COMMENT "Comment"
IDS_COMMENT2 "&Comment:"
diff --git a/CPP/7zip/UI/GUI/CompressDialog.cpp b/CPP/7zip/UI/GUI/CompressDialog.cpp
index 64ee31d8..04a40a43 100755
--- a/CPP/7zip/UI/GUI/CompressDialog.cpp
+++ b/CPP/7zip/UI/GUI/CompressDialog.cpp
@@ -2,19 +2,19 @@
#include "StdAfx.h"
-#include "resource.h"
#include "Common/Defs.h"
-#include "Common/StringConvert.h"
#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
+
#include "Windows/CommonDialog.h"
#include "Windows/FileDir.h"
#include "Windows/FileName.h"
#include "Windows/ResourceString.h"
#include "Windows/System.h"
+#include "../FileManager/FormatUtils.h"
#include "../FileManager/HelpUtils.h"
#include "../FileManager/SplitUtils.h"
-#include "../FileManager/FormatUtils.h"
#include "../Explorer/MyMessages.h"
@@ -22,6 +22,8 @@
#include "CompressDialog.h"
+#include "resource.h"
+
#ifndef _UNICODE
extern bool g_IsNT;
#endif
@@ -112,6 +114,7 @@ enum EMethodID
{
kCopy,
kLZMA,
+ kLZMA2,
kPPMd,
kBZip2,
kDeflate,
@@ -122,6 +125,7 @@ static const LPCWSTR kMethodsNames[] =
{
L"Copy",
L"LZMA",
+ L"LZMA2",
L"PPMd",
L"BZip2",
L"Deflate",
@@ -131,6 +135,7 @@ static const LPCWSTR kMethodsNames[] =
static const EMethodID g_7zMethods[] =
{
kLZMA,
+ kLZMA2,
kPPMd,
kBZip2
};
@@ -139,6 +144,7 @@ static const EMethodID g_7zSfxMethods[] =
{
kCopy,
kLZMA,
+ kLZMA2,
kPPMd
};
@@ -160,6 +166,11 @@ static EMethodID g_BZip2Methods[] =
kBZip2
};
+static EMethodID g_XzMethods[] =
+{
+ kLZMA2
+};
+
struct CFormatInfo
{
LPCWSTR Name;
@@ -206,7 +217,13 @@ static const CFormatInfo g_Formats[] =
L"BZip2",
(1 << 1) | (1 << 3) | (1 << 5) | (1 << 7) | (1 << 9),
METHODS_PAIR(g_BZip2Methods),
- false, false, true, false, false
+ false, false, true, false, false, false
+ },
+ {
+ L"xz",
+ (1 << 1) | (1 << 3) | (1 << 5) | (1 << 7) | (1 << 9),
+ METHODS_PAIR(g_XzMethods),
+ false, false, true, false, false, false
},
{
L"Tar",
@@ -273,20 +290,23 @@ bool CCompressDialog::OnInit()
Info.ArchiverInfoIndex = 0;
int i;
- for(i = 0; i < m_ArchiverInfoList.Size(); i++)
+ for (i = 0; i < m_ArchiverInfoList.Size(); i++)
{
const CArcInfoEx &ai = m_ArchiverInfoList[i];
- m_Format.AddString(ai.Name);
- if (ai.Name.CompareNoCase(m_RegistryInfo.ArchiveType) == 0)
+ int index = (int)m_Format.AddString(ai.Name);
+ m_Format.SetItemData(index, i);
+ if (ai.Name.CompareNoCase(m_RegistryInfo.ArchiveType) == 0 || i == 0)
+ {
+ m_Format.SetCurSel(index);
Info.ArchiverInfoIndex = i;
+ }
}
- m_Format.SetCurSel(Info.ArchiverInfoIndex);
SetArchiveName(Info.ArchiveName);
SetLevel();
SetParams();
- for(i = 0; i < m_RegistryInfo.HistoryArchives.Size() && i < kHistorySize; i++)
+ for (i = 0; i < m_RegistryInfo.HistoryArchives.Size() && i < kHistorySize; i++)
m_ArchivePath.AddString(m_RegistryInfo.HistoryArchives[i]);
m_UpdateMode.AddString(LangString(IDS_COMPRESS_UPDATE_MODE_ADD, 0x02000DA1));
@@ -300,7 +320,7 @@ bool CCompressDialog::OnInit()
SetNumThreads();
TCHAR s[40] = { TEXT('/'), TEXT(' '), 0 };
- ConvertUInt64ToString(NSystem::GetNumberOfProcessors(), s + 2);
+ ConvertUInt32ToString(NSystem::GetNumberOfProcessors(), s + 2);
SetItemText(IDC_COMPRESS_HARDWARE_THREADS, s);
CheckButton(IDC_COMPRESS_SFX, Info.SFXMode);
@@ -423,7 +443,7 @@ bool CCompressDialog::IsSFX()
void CCompressDialog::OnButtonSFX()
{
- SetMethod();
+ SetMethod(GetMethodID());
UString fileName;
m_ArchivePath.GetText(fileName);
@@ -431,8 +451,7 @@ void CCompressDialog::OnButtonSFX()
int slashPos = fileName.ReverseFind(WCHAR_PATH_SEPARATOR);
if (dotPos < 0 || dotPos <= slashPos)
dotPos = -1;
- bool isSFX = IsSFX();
- if (isSFX)
+ if (IsSFX())
{
if (dotPos >= 0)
fileName = fileName.Left(dotPos);
@@ -545,7 +564,7 @@ void CCompressDialog::OnOK()
Info.Method = GetMethodSpec();
Info.EncryptionMethod = GetEncryptionMethodSpec();
- Info.ArchiverInfoIndex = m_Format.GetCurSel();
+ Info.ArchiverInfoIndex = GetFormatIndex();
Info.SFXMode = IsSFX();
Info.OpenShareForWrite = IsButtonCheckedBool(IDC_COMPRESS_SHARED);
@@ -577,7 +596,7 @@ void CCompressDialog::OnOK()
}
}
- for(int i = 0; i < m_ArchivePath.GetCount(); i++)
+ for (int i = 0; i < m_ArchivePath.GetCount(); i++)
{
UString sTemp;
m_ArchivePath.GetLBText(i, sTemp);
@@ -624,7 +643,7 @@ bool CCompressDialog::OnCommand(int code, int itemID, LPARAM lParam)
}
case IDC_COMPRESS_COMBO_LEVEL:
{
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormatAlways(ai.Name);
NCompression::CFormatOptions &fo = m_RegistryInfo.FormatOptionsVector[index];
fo.ResetForLevelChange();
@@ -697,7 +716,7 @@ void CCompressDialog::SetArchiveName2(bool prevWasSFX)
void CCompressDialog::SetArchiveName(const UString &name)
{
UString fileName = name;
- Info.ArchiverInfoIndex = m_Format.GetCurSel();
+ Info.ArchiverInfoIndex = GetFormatIndex();
const CArcInfoEx &ai = m_ArchiverInfoList[Info.ArchiverInfoIndex];
m_PrevFormat = Info.ArchiverInfoIndex;
if (ai.KeepName)
@@ -750,7 +769,7 @@ int CCompressDialog::FindRegistryFormatAlways(const UString &name)
int CCompressDialog::GetStaticFormatIndex()
{
- int formatIndex = m_Format.GetCurSel();
+ int formatIndex = GetFormatIndex();
const CArcInfoEx &ai = m_ArchiverInfoList[formatIndex];
for (int i = 0; i < MY_SIZE_OF_ARRAY(g_Formats); i++)
if (ai.Name.CompareNoCase(g_Formats[i].Name) == 0)
@@ -774,7 +793,7 @@ void CCompressDialog::SetLevel()
{
m_Level.ResetContent();
const CFormatInfo &fi = g_Formats[GetStaticFormatIndex()];
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
UInt32 level = kNormal;
if (index >= 0)
@@ -799,7 +818,7 @@ void CCompressDialog::SetLevel()
SetMethod();
}
-void CCompressDialog::SetMethod()
+void CCompressDialog::SetMethod(int keepMethodId)
{
m_Method.ResetContent();
UInt32 level = GetLevel();
@@ -810,7 +829,7 @@ void CCompressDialog::SetMethod()
return;
}
const CFormatInfo &fi = g_Formats[GetStaticFormatIndex()];
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
UString defaultMethod;
if (index >= 0)
@@ -819,7 +838,8 @@ void CCompressDialog::SetMethod()
defaultMethod = fo.Method;
}
bool isSfx = IsSFX();
- for(int m = 0; m < fi.NumMethods; m++)
+ bool weUseSameMethod = false;
+ for (int m = 0; m < fi.NumMethods; m++)
{
EMethodID methodID = fi.MathodIDs[m];
if (isSfx)
@@ -827,23 +847,32 @@ void CCompressDialog::SetMethod()
continue;
const LPCWSTR method = kMethodsNames[methodID];
int itemIndex = (int)m_Method.AddString(GetSystemString(method));
- if (defaultMethod.CompareNoCase(method) == 0 || m == 0)
+ if (keepMethodId == methodID)
+ {
m_Method.SetCurSel(itemIndex);
+ weUseSameMethod = true;
+ continue;
+ }
+ if ((defaultMethod.CompareNoCase(method) == 0 || m == 0) && !weUseSameMethod)
+ m_Method.SetCurSel(itemIndex);
+ }
+ if (!weUseSameMethod)
+ {
+ SetDictionary();
+ SetOrder();
}
- SetDictionary();
- SetOrder();
}
bool CCompressDialog::IsZipFormat()
{
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
return (ai.Name.CompareNoCase(L"zip") == 0);
}
void CCompressDialog::SetEncryptionMethod()
{
_encryptionMethod.ResetContent();
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
if (ai.Name.CompareNoCase(L"7z") == 0)
{
_encryptionMethod.AddString(TEXT("AES-256"));
@@ -903,7 +932,7 @@ int CCompressDialog::AddDictionarySize(UInt32 size, bool kilo, bool maga)
else if (maga)
sizePrint >>= 20;
TCHAR s[40];
- ConvertUInt64ToString(sizePrint, s);
+ ConvertUInt32ToString(sizePrint, s);
if (kilo)
lstrcat(s, TEXT(" K"));
else if (maga)
@@ -931,7 +960,7 @@ int CCompressDialog::AddDictionarySize(UInt32 size)
void CCompressDialog::SetDictionary()
{
m_Dictionary.ResetContent();
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
UInt32 defaultDictionary = UInt32(-1);
if (index >= 0)
@@ -948,6 +977,7 @@ void CCompressDialog::SetDictionary()
switch (methodID)
{
case kLZMA:
+ case kLZMA2:
{
static const UInt32 kMinDicSize = (1 << 16);
if (defaultDictionary == UInt32(-1))
@@ -1066,7 +1096,7 @@ UInt32 CCompressDialog::GetLevel2()
int CCompressDialog::AddOrder(UInt32 size)
{
TCHAR s[40];
- ConvertUInt64ToString(size, s);
+ ConvertUInt32ToString(size, s);
int index = (int)m_Order.AddString(s);
m_Order.SetItemData(index, size);
return index;
@@ -1075,7 +1105,7 @@ int CCompressDialog::AddOrder(UInt32 size)
void CCompressDialog::SetOrder()
{
m_Order.ResetContent();
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
UInt32 defaultOrder = UInt32(-1);
if (index >= 0)
@@ -1091,6 +1121,7 @@ void CCompressDialog::SetOrder()
switch (methodID)
{
case kLZMA:
+ case kLZMA2:
{
if (defaultOrder == UInt32(-1))
defaultOrder = (level >= 7) ? 64 : 32;
@@ -1193,7 +1224,7 @@ void CCompressDialog::SetSolidBlockSize()
UInt32 defaultBlockSize = (UInt32)-1;
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
if (index >= 0)
{
@@ -1211,7 +1242,7 @@ void CCompressDialog::SetSolidBlockSize()
if (needSet && dictionary >= (((UInt64)1 << (i - 7))) && i <= 32)
defaultBlockSize = i;
TCHAR s[40];
- ConvertUInt64ToString(1 << (i % 10), s);
+ ConvertUInt32ToString(1 << (i % 10), s);
if (i < 30) lstrcat(s, TEXT(" M"));
else lstrcat(s, TEXT(" G"));
lstrcat(s, TEXT("B"));
@@ -1237,7 +1268,7 @@ void CCompressDialog::SetNumThreads()
UInt32 numHardwareThreads = NSystem::GetNumberOfProcessors();
UInt32 defaultValue = numHardwareThreads;
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
int index = FindRegistryFormat(ai.Name);
if (index >= 0)
{
@@ -1250,23 +1281,16 @@ void CCompressDialog::SetNumThreads()
int methodID = GetMethodID();
switch (methodID)
{
- case kLZMA:
- {
- numAlgoThreadsMax = 2;
- break;
- }
- case kBZip2:
- {
- numAlgoThreadsMax = 32;
- break;
- }
+ case kLZMA: numAlgoThreadsMax = 2; break;
+ case kLZMA2: numAlgoThreadsMax = 32; break;
+ case kBZip2: numAlgoThreadsMax = 32; break;
}
if (IsZipFormat())
numAlgoThreadsMax = 128;
for (UInt32 i = 1; i <= numHardwareThreads * 2 && i <= numAlgoThreadsMax; i++)
{
TCHAR s[40];
- ConvertUInt64ToString(i, s);
+ ConvertUInt32ToString(i, s);
int index = (int)m_NumThreads.AddString(s);
m_NumThreads.SetItemData(index, (UInt32)i);
}
@@ -1298,9 +1322,11 @@ UInt64 CCompressDialog::GetMemoryUsage(UInt32 dictionary, UInt64 &decompressMemo
if (numMainThreads > 1)
size += (UInt64)numMainThreads << 25;
}
- switch (GetMethodID())
+ int methidId = GetMethodID();
+ switch (methidId)
{
case kLZMA:
+ case kLZMA2:
{
UInt32 hs = dictionary - 1;
hs |= (hs >> 1);
@@ -1313,7 +1339,7 @@ UInt64 CCompressDialog::GetMemoryUsage(UInt32 dictionary, UInt64 &decompressMemo
hs >>= 1;
hs++;
UInt64 size1 = (UInt64)hs * 4;
- size1 += (UInt64)dictionary * 11 / 2;
+ size1 += (UInt64)dictionary * 4;
if (level >= 5)
size1 += (UInt64)dictionary * 4;
size1 += (2 << 20);
@@ -1324,7 +1350,18 @@ UInt64 CCompressDialog::GetMemoryUsage(UInt32 dictionary, UInt64 &decompressMemo
size1 += (2 << 20) + (4 << 20);
numThreads1 = 2;
}
- size += size1 * numThreads / numThreads1;
+ UInt32 numBlockThreads = numThreads / numThreads1;
+ if (methidId == kLZMA || numBlockThreads == 1)
+ size1 += (UInt64)dictionary * 3 / 2;
+ else
+ {
+ UInt64 chunkSize = (UInt64)dictionary << 2;
+ chunkSize = MyMax(chunkSize, (UInt64)(1 << 20));
+ chunkSize = MyMin(chunkSize, (UInt64)(1 << 28));
+ chunkSize = MyMax(chunkSize, (UInt64)dictionary);
+ size1 += chunkSize * 2;
+ }
+ size += size1 * numBlockThreads;
decompressMemory = dictionary + (2 << 20);
return size;
@@ -1363,7 +1400,7 @@ UInt64 CCompressDialog::GetMemoryUsage(UInt64 &decompressMemory)
void CCompressDialog::PrintMemUsage(UINT res, UInt64 value)
{
- if (value == (UInt64)Int64(-1))
+ if (value == (UInt64)(Int64)-1)
{
SetItemText(res, TEXT("?"));
return;
@@ -1385,7 +1422,7 @@ void CCompressDialog::SetMemoryUsage()
void CCompressDialog::SetParams()
{
- const CArcInfoEx &ai = m_ArchiverInfoList[m_Format.GetCurSel()];
+ const CArcInfoEx &ai = m_ArchiverInfoList[GetFormatIndex()];
m_Params.SetText(TEXT(""));
int index = FindRegistryFormat(ai.Name);
if (index >= 0)
@@ -1411,3 +1448,8 @@ void CCompressDialog::SaveOptionsInMem()
fo.NumThreads = GetNumThreadsSpec();
fo.BlockLogSize = GetBlockSizeSpec();
}
+
+int CCompressDialog::GetFormatIndex()
+{
+ return (int)m_Format.GetItemData(m_Format.GetCurSel());
+}
diff --git a/CPP/7zip/UI/GUI/CompressDialog.h b/CPP/7zip/UI/GUI/CompressDialog.h
index a88d472c..75eeeee8 100755
--- a/CPP/7zip/UI/GUI/CompressDialog.h
+++ b/CPP/7zip/UI/GUI/CompressDialog.h
@@ -1,15 +1,16 @@
// CompressDialog.h
-#ifndef __COMPRESSDIALOG_H
-#define __COMPRESSDIALOG_H
-
-#include "../Common/ZipRegistry.h"
-#include "../Common/LoadCodecs.h"
-#include "CompressDialogRes.h"
+#ifndef __COMPRESS_DIALOG_H
+#define __COMPRESS_DIALOG_H
+#include "Windows/Control/ComboBox.h"
#include "Windows/Control/Dialog.h"
#include "Windows/Control/Edit.h"
-#include "Windows/Control/ComboBox.h"
+
+#include "../Common/LoadCodecs.h"
+#include "../Common/ZipRegistry.h"
+
+#include "CompressDialogRes.h"
namespace NCompressDialog
{
@@ -107,7 +108,7 @@ class CCompressDialog: public NWindows::NControl::CModalDialog
void SetLevel();
- void SetMethod();
+ void SetMethod(int keepMethodId = -1);
int GetMethodID();
UString GetMethodSpec();
UString GetEncryptionMethodSpec();
@@ -151,6 +152,8 @@ class CCompressDialog: public NWindows::NControl::CModalDialog
void UpdatePasswordControl();
bool IsShowPasswordChecked() const
{ return IsButtonChecked(IDC_COMPRESS_CHECK_SHOW_PASSWORD) == BST_CHECKED; }
+
+ int GetFormatIndex();
public:
CObjectVector<CArcInfoEx> m_ArchiverInfoList;
diff --git a/CPP/7zip/UI/GUI/CompressDialog.rc b/CPP/7zip/UI/GUI/CompressDialog.rc
index 397a2756..8e79f1bf 100755
--- a/CPP/7zip/UI/GUI/CompressDialog.rc
+++ b/CPP/7zip/UI/GUI/CompressDialog.rc
@@ -58,7 +58,7 @@ BEGIN
PUSHBUTTON "...", IDC_COMPRESS_BUTTON_SET_ARCHIVE, xSize - marg - bDotsSize, 17, bDotsSize, bYSize, WS_GROUP
LTEXT "Archive &format:", IDC_STATIC_COMPRESS_FORMAT, marg, 41, g0XSize, 8
- COMBOBOX IDC_COMPRESS_COMBO_FORMAT, g1XPos, 39, g1XSize , 80,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
+ COMBOBOX IDC_COMPRESS_COMBO_FORMAT, g1XPos, 39, g1XSize , 80,CBS_DROPDOWNLIST | CBS_SORT | WS_VSCROLL | WS_TABSTOP
LTEXT "Compression &level:",IDC_STATIC_COMPRESS_LEVEL, marg, 62, g0XSize, 8
COMBOBOX IDC_COMPRESS_COMBO_LEVEL, g1XPos, 60, g1XSize, 80,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP
diff --git a/CPP/7zip/UI/GUI/ExtractGUI.cpp b/CPP/7zip/UI/GUI/ExtractGUI.cpp
index a03bd77a..95864d2c 100755
--- a/CPP/7zip/UI/GUI/ExtractGUI.cpp
+++ b/CPP/7zip/UI/GUI/ExtractGUI.cpp
@@ -2,26 +2,27 @@
#include "StdAfx.h"
-#include "ExtractGUI.h"
-
-#include "Common/StringConvert.h"
#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
-#include "Windows/FileDir.h"
#include "Windows/Error.h"
+#include "Windows/FileDir.h"
#include "Windows/FileFind.h"
#include "Windows/Thread.h"
-#include "../FileManager/FormatUtils.h"
#include "../FileManager/ExtractCallback.h"
+#include "../FileManager/FormatUtils.h"
#include "../FileManager/LangUtils.h"
#include "../Common/ArchiveExtractCallback.h"
+#include "../Common/PropIDUtils.h"
+
#include "../Explorer/MyMessages.h"
+
#include "resource.h"
#include "ExtractRes.h"
-
#include "ExtractDialog.h"
+#include "ExtractGUI.h"
using namespace NWindows;
@@ -198,6 +199,16 @@ HRESULT ExtractGUI(
AddValuePair(IDS_FILES_COLON, 0x02000320, extracter.Stat.NumFiles, s);
AddSizePair(IDS_SIZE_COLON, 0x02000322, extracter.Stat.UnpackSize, s);
AddSizePair(IDS_COMPRESSED_COLON, 0x02000323, extracter.Stat.PackSize, s);
+
+ if (options.CalcCrc)
+ {
+ wchar_t temp[16];
+ ConvertUInt32ToHex(extracter.Stat.CrcSum, temp);
+ s += L"CRC: ";
+ s += temp;
+ s += L"\n";
+ }
+
s += L"\n";
s += LangString(IDS_MESSAGE_NO_ERRORS, 0x02000608);
@@ -209,5 +220,3 @@ HRESULT ExtractGUI(
throw extracter.ErrorMessage;
return extracter.Result;
}
-
-
diff --git a/CPP/7zip/UI/GUI/GUI.cpp b/CPP/7zip/UI/GUI/GUI.cpp
index e1117188..3a1a633e 100755
--- a/CPP/7zip/UI/GUI/GUI.cpp
+++ b/CPP/7zip/UI/GUI/GUI.cpp
@@ -4,31 +4,27 @@
#include <initguid.h>
-extern "C"
-{
- #include "../../../../C/Alloc.h"
-}
+#include "../../../../C/Alloc.h"
-#include "Common/NewHandler.h"
-#include "Common/StringConvert.h"
#include "Common/CommandLineParser.h"
#include "Common/MyException.h"
+#include "Common/StringConvert.h"
#include "Windows/Error.h"
#ifdef _WIN32
#include "Windows/MemoryLock.h"
#endif
-#include "../FileManager/StringUtils.h"
-
-#include "../Common/ExitCode.h"
#include "../Common/ArchiveCommandLine.h"
+#include "../Common/ExitCode.h"
-#include "ExtractRes.h"
+#include "../FileManager/StringUtils.h"
+#include "BenchmarkDialog.h"
#include "ExtractGUI.h"
#include "UpdateGUI.h"
-#include "BenchmarkDialog.h"
+
+#include "ExtractRes.h"
using namespace NWindows;
@@ -119,8 +115,12 @@ static int Main2()
CExtractCallbackImp *ecs = new CExtractCallbackImp;
CMyComPtr<IFolderArchiveExtractCallback> extractCallback = ecs;
ecs->ProgressDialog.CompressingMode = false;
+
+ #ifndef _NO_CRYPTO
ecs->PasswordIsDefined = options.PasswordEnabled;
ecs->Password = options.Password;
+ #endif
+
ecs->Init();
CExtractOptions eo;
@@ -130,6 +130,7 @@ static int Main2()
eo.OverwriteMode = options.OverwriteMode;
eo.PathMode = options.Command.GetPathMode();
eo.TestMode = options.Command.IsTestMode();
+ eo.CalcCrc = options.CalcCrc;
#ifdef COMPRESS_MT
eo.Properties = options.ExtractProperties;
#endif
@@ -146,14 +147,19 @@ static int Main2()
}
else if (options.Command.IsFromUpdateGroup())
{
- bool passwordIsDefined =
- options.PasswordEnabled && !options.Password.IsEmpty();
+ #ifndef _NO_CRYPTO
+ bool passwordIsDefined = options.PasswordEnabled && !options.Password.IsEmpty();
+ #endif
CUpdateCallbackGUI callback;
// callback.EnablePercents = options.EnablePercents;
+
+ #ifndef _NO_CRYPTO
callback.PasswordIsDefined = passwordIsDefined;
callback.AskPassword = options.PasswordEnabled && options.Password.IsEmpty();
callback.Password = options.Password;
+ #endif
+
// callback.StdOutMode = options.UpdateOptions.StdOutMode;
callback.Init();
diff --git a/CPP/7zip/UI/GUI/GUI.dsp b/CPP/7zip/UI/GUI/GUI.dsp
index e5fbec0e..42c83c60 100755
--- a/CPP/7zip/UI/GUI/GUI.dsp
+++ b/CPP/7zip/UI/GUI/GUI.dsp
@@ -45,7 +45,7 @@ RSC=rc.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"stdafx.h" /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /Yu"stdafx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"stdafx.h" /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "NDEBUG"
@@ -72,7 +72,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"stdafx.h" /FD /GZ /c
-# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /Yu"stdafx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_MBCS" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"stdafx.h" /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "_DEBUG"
@@ -99,7 +99,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MD /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"stdafx.h" /FD /c
-# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /Yu"stdafx.h" /FD /c
+# ADD CPP /nologo /Gz /MD /W3 /GX /O1 /I "..\..\..\\" /D "NDEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"stdafx.h" /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "NDEBUG"
@@ -127,7 +127,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MDd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /Yu"stdafx.h" /FD /GZ /c
-# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /Yu"stdafx.h" /FD /GZ /c
+# ADD CPP /nologo /Gz /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\\" /D "_DEBUG" /D "_UNICODE" /D "UNICODE" /D "WIN32" /D "_WINDOWS" /D "LANG" /D "COMPRESS_MT" /D "WIN_LONG_PATH" /D "EXTERNAL_LZMA" /D "EXTERNAL_CODECS" /D "BENCH_MT" /D "SUPPORT_DEVICE_FILE" /Yu"stdafx.h" /FD /GZ /c
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x419 /d "_DEBUG"
@@ -379,91 +379,63 @@ SOURCE=..\Explorer\MyMessages.h
# Begin Group "Dialogs"
# PROP Default_Filter ""
-# Begin Group "Progress"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\FileManager\ProgressDialog2.cpp
+SOURCE=.\BenchmarkDialog.cpp
# End Source File
# Begin Source File
-SOURCE=..\FileManager\ProgressDialog2.h
+SOURCE=.\BenchmarkDialog.h
# End Source File
-# End Group
-# Begin Group "Messages"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\FileManager\MessagesDialog.cpp
+SOURCE=.\CompressDialog.cpp
# End Source File
# Begin Source File
-SOURCE=..\FileManager\MessagesDialog.h
+SOURCE=.\CompressDialog.h
# End Source File
-# End Group
-# Begin Group "Overwtite"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\FileManager\OverwriteDialog.cpp
+SOURCE=.\ExtractDialog.cpp
# End Source File
# Begin Source File
-SOURCE=..\FileManager\OverwriteDialog.h
+SOURCE=.\ExtractDialog.h
# End Source File
-# End Group
-# Begin Group "Password"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=..\FileManager\PasswordDialog.cpp
+SOURCE=..\FileManager\MessagesDialog.cpp
# End Source File
# Begin Source File
-SOURCE=..\FileManager\PasswordDialog.h
+SOURCE=..\FileManager\MessagesDialog.h
# End Source File
-# End Group
-# Begin Group "Compress Dialog"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=.\CompressDialog.cpp
+SOURCE=..\FileManager\OverwriteDialog.cpp
# End Source File
# Begin Source File
-SOURCE=.\CompressDialog.h
+SOURCE=..\FileManager\OverwriteDialog.h
# End Source File
-# End Group
-# Begin Group "Extract Dialog"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=.\ExtractDialog.cpp
+SOURCE=..\FileManager\PasswordDialog.cpp
# End Source File
# Begin Source File
-SOURCE=.\ExtractDialog.h
+SOURCE=..\FileManager\PasswordDialog.h
# End Source File
-# End Group
-# Begin Group "Benchmark Dialog"
-
-# PROP Default_Filter ""
# Begin Source File
-SOURCE=.\BenchmarkDialog.cpp
+SOURCE=..\FileManager\ProgressDialog2.cpp
# End Source File
# Begin Source File
-SOURCE=.\BenchmarkDialog.h
+SOURCE=..\FileManager\ProgressDialog2.h
# End Source File
# End Group
-# End Group
# Begin Group "FM Common"
# PROP Default_Filter ""
@@ -962,5 +934,17 @@ SOURCE=..\..\..\Windows\Window.cpp
SOURCE=..\..\..\Windows\Window.h
# End Source File
# End Group
+# Begin Group "Archive Common"
+
+# PROP Default_Filter ""
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.cpp
+# End Source File
+# Begin Source File
+
+SOURCE=..\..\Archive\Common\OutStreamWithCRC.h
+# End Source File
+# End Group
# End Target
# End Project
diff --git a/CPP/7zip/UI/GUI/UpdateCallbackGUI.cpp b/CPP/7zip/UI/GUI/UpdateCallbackGUI.cpp
index 10c0a798..07c74e9b 100755
--- a/CPP/7zip/UI/GUI/UpdateCallbackGUI.cpp
+++ b/CPP/7zip/UI/GUI/UpdateCallbackGUI.cpp
@@ -156,6 +156,7 @@ HRESULT CUpdateCallbackGUI::SetOperationResult(Int32 /* operationResult */)
HRESULT CUpdateCallbackGUI::CryptoGetTextPassword2(Int32 *passwordIsDefined, BSTR *password)
{
+ *password = NULL;
if (!PasswordIsDefined)
{
if (AskPassword)
@@ -171,6 +172,20 @@ HRESULT CUpdateCallbackGUI::CryptoGetTextPassword2(Int32 *passwordIsDefined, BST
return StringToBstr(Password, password);
}
+HRESULT CUpdateCallbackGUI::CryptoGetTextPassword(BSTR *password)
+{
+ *password = NULL;
+ if (!PasswordIsDefined)
+ {
+ CPasswordDialog dialog;
+ if (dialog.Create(ProgressDialog) == IDCANCEL)
+ return E_ABORT;
+ Password = dialog.Password;
+ PasswordIsDefined = true;
+ }
+ return StringToBstr(Password, password);
+}
+
/*
It doesn't work, since main stream waits Dialog
HRESULT CUpdateCallbackGUI::CloseProgress()
diff --git a/CPP/7zip/UI/GUI/UpdateGUI.cpp b/CPP/7zip/UI/GUI/UpdateGUI.cpp
index ef9a2d70..2d4dbbc2 100755
--- a/CPP/7zip/UI/GUI/UpdateGUI.cpp
+++ b/CPP/7zip/UI/GUI/UpdateGUI.cpp
@@ -4,32 +4,28 @@
#include "UpdateGUI.h"
-#include "resource.h"
-#include "Common/StringConvert.h"
#include "Common/IntToString.h"
+#include "Common/StringConvert.h"
#include "Common/StringToInt.h"
-#include "Windows/FileDir.h"
#include "Windows/Error.h"
-#include "Windows/FileFind.h"
+#include "Windows/FileDir.h"
#include "Windows/Thread.h"
-#include "../FileManager/FormatUtils.h"
-#include "../FileManager/ExtractCallback.h"
-#include "../FileManager/StringUtils.h"
-
-#include "../Common/ArchiveExtractCallback.h"
#include "../Common/WorkDir.h"
+
#include "../Explorer/MyMessages.h"
-#include "ExtractRes.h"
+
+#include "../FileManager/StringUtils.h"
#include "CompressDialog.h"
#include "UpdateGUI.h"
+#include "resource.h"
+
using namespace NWindows;
using namespace NFile;
-// static const wchar_t *kIncorrectOutDir = L"Incorrect output directory path";
static const wchar_t *kDefaultSfxModule = L"7z.sfx";
static const wchar_t *kSFXExtension = L"exe";
@@ -242,7 +238,7 @@ static HRESULT ShowDialog(
name += WCHAR_PATH_SEPARATOR;
name += item.PathParts[i];
}
- if (NFind::FindFile(name, fileInfo))
+ if (fileInfo.Find(name))
{
if (censor.Pairs.Size() == 1 && pair.Head.IncludeItems.Size() == 1)
oneFile = !fileInfo.IsDir();
@@ -355,7 +351,7 @@ static HRESULT ShowDialog(
UString fullPath;
NDirectory::MyGetFullPathName(di.ArchiveName, fullPath);
options.WorkingDir = GetWorkDir(workDirInfo, fullPath);
- NFile::NDirectory::CreateComplexDirectory(options.WorkingDir);
+ NDirectory::CreateComplexDirectory(options.WorkingDir);
}
return S_OK;
}
diff --git a/CPP/7zip/UI/GUI/makefile b/CPP/7zip/UI/GUI/makefile
index b92935ab..233e2ee2 100755
--- a/CPP/7zip/UI/GUI/makefile
+++ b/CPP/7zip/UI/GUI/makefile
@@ -8,6 +8,7 @@ CFLAGS = $(CFLAGS) -I ../../../ \
-DEXTERNAL_CODECS \
-DBENCH_MT \
-D_7ZIP_LARGE_PAGES \
+ -DSUPPORT_DEVICE_FILE \
GUI_OBJS = \
$O\BenchmarkDialog.obj \
@@ -85,6 +86,9 @@ UI_COMMON_OBJS = \
$O\WorkDir.obj \
$O\ZipRegistry.obj \
+AR_COMMON_OBJS = \
+ $O\OutStreamWithCRC.obj \
+
LZMA_BENCH_OBJS = \
$O\LzmaBench.obj \
@@ -117,6 +121,7 @@ OBJS = \
$(WIN_CTRL_OBJS) \
$(7ZIP_COMMON_OBJS) \
$(UI_COMMON_OBJS) \
+ $(AR_COMMON_OBJS) \
$(FM_OBJS)\
$O\MyMessages.obj \
$O\CopyCoder.obj \
@@ -139,6 +144,8 @@ $(7ZIP_COMMON_OBJS): ../../Common/$(*B).cpp
$(COMPL)
$(UI_COMMON_OBJS): ../Common/$(*B).cpp
$(COMPL)
+$(AR_COMMON_OBJS): ../../Archive/Common/$(*B).cpp
+ $(COMPL)
$(FM_OBJS): ../FileManager/$(*B).cpp
$(COMPL)
$O\MyMessages.obj: ../Explorer/MyMessages.cpp
diff --git a/CPP/Common/CRC.cpp b/CPP/Common/CRC.cpp
index a1e54ec9..9a9f81fb 100755
--- a/CPP/Common/CRC.cpp
+++ b/CPP/Common/CRC.cpp
@@ -2,9 +2,6 @@
#include "StdAfx.h"
-extern "C"
-{
#include "../../C/7zCrc.h"
-}
struct CCRCTableInit { CCRCTableInit() { CrcGenerateTable(); } } g_CRCTableInit;
diff --git a/CPP/Common/IntToString.cpp b/CPP/Common/IntToString.cpp
index beda203d..31070b41 100755
--- a/CPP/Common/IntToString.cpp
+++ b/CPP/Common/IntToString.cpp
@@ -42,6 +42,9 @@ void ConvertUInt64ToString(UInt64 value, wchar_t *s)
*s = L'\0';
}
+void ConvertUInt32ToString(UInt32 value, char *s) { ConvertUInt64ToString(value, s); }
+void ConvertUInt32ToString(UInt32 value, wchar_t *s) { ConvertUInt64ToString(value, s); }
+
void ConvertInt64ToString(Int64 value, char *s)
{
if (value < 0)
diff --git a/CPP/Common/IntToString.h b/CPP/Common/IntToString.h
index cf86090f..bad17e4a 100755
--- a/CPP/Common/IntToString.h
+++ b/CPP/Common/IntToString.h
@@ -1,15 +1,17 @@
// Common/IntToString.h
-#ifndef __COMMON_INTTOSTRING_H
-#define __COMMON_INTTOSTRING_H
+#ifndef __COMMON_INT_TO_STRING_H
+#define __COMMON_INT_TO_STRING_H
#include <stddef.h>
#include "Types.h"
void ConvertUInt64ToString(UInt64 value, char *s, UInt32 base = 10);
void ConvertUInt64ToString(UInt64 value, wchar_t *s);
-
void ConvertInt64ToString(Int64 value, char *s);
void ConvertInt64ToString(Int64 value, wchar_t *s);
+void ConvertUInt32ToString(UInt32 value, char *s);
+void ConvertUInt32ToString(UInt32 value, wchar_t *s);
+
#endif
diff --git a/CPP/Common/MyXml.cpp b/CPP/Common/MyXml.cpp
index 1d5d836a..8aa9ce8c 100755
--- a/CPP/Common/MyXml.cpp
+++ b/CPP/Common/MyXml.cpp
@@ -18,7 +18,7 @@ static bool IsSpaceChar(char c)
return (c == ' ' || c == '\t' || c == 0x0D || c == 0x0A);
}
-#define SKEEP_SPACES(s, pos) while (IsSpaceChar(s[pos])) pos++;
+#define SKIP_SPACES(s, pos) while (IsSpaceChar(s[pos])) pos++;
static bool ReadProperty(const AString &s, int &pos, CXmlProp &prop)
{
@@ -35,11 +35,11 @@ static bool ReadProperty(const AString &s, int &pos, CXmlProp &prop)
if (prop.Name.IsEmpty())
return false;
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
if (s[pos++] != '=')
return false;
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
if (s[pos++] != '\"')
return false;
@@ -109,7 +109,7 @@ bool CXmlItem::ParseItems(const AString &s, int &pos, int numAllowedLevels)
AString finishString = "</";
for (;;)
{
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
if (s.Mid(pos, finishString.Length()) == finishString)
return true;
@@ -123,7 +123,7 @@ bool CXmlItem::ParseItems(const AString &s, int &pos, int numAllowedLevels)
bool CXmlItem::ParseItem(const AString &s, int &pos, int numAllowedLevels)
{
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
int pos2 = s.Find('<', pos);
if (pos2 < 0)
@@ -138,7 +138,7 @@ bool CXmlItem::ParseItem(const AString &s, int &pos, int numAllowedLevels)
IsTag = true;
pos++;
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
for (; pos < s.Length(); pos++)
{
@@ -153,11 +153,11 @@ bool CXmlItem::ParseItem(const AString &s, int &pos, int numAllowedLevels)
int posTemp = pos;
for (;;)
{
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
if (s[pos] == '/')
{
pos++;
- // SKEEP_SPACES(s, pos);
+ // SKIP_SPACES(s, pos);
return (s[pos++] == '>');
}
if (s[pos] == '>')
@@ -181,16 +181,16 @@ bool CXmlItem::ParseItem(const AString &s, int &pos, int numAllowedLevels)
}
}
-bool SkeepHeader(const AString &s, int &pos, const AString &startString, const AString &endString)
+static bool SkipHeader(const AString &s, int &pos, const AString &startString, const AString &endString)
{
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
if (s.Mid(pos, startString.Length()) == startString)
{
pos = s.Find(endString, pos);
if (pos < 0)
return false;
pos += endString.Length();
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
}
return true;
}
@@ -198,12 +198,12 @@ bool SkeepHeader(const AString &s, int &pos, const AString &startString, const A
bool CXml::Parse(const AString &s)
{
int pos = 0;
- if (!SkeepHeader(s, pos, "<?xml", "?>"))
+ if (!SkipHeader(s, pos, "<?xml", "?>"))
return false;
- if (!SkeepHeader(s, pos, "<!DOCTYPE", ">"))
+ if (!SkipHeader(s, pos, "<!DOCTYPE", ">"))
return false;
if (!Root.ParseItem(s, pos, 1000))
return false;
- SKEEP_SPACES(s, pos);
+ SKIP_SPACES(s, pos);
return (pos == s.Length() && Root.IsTag);
}
diff --git a/CPP/Common/StdInStream.cpp b/CPP/Common/StdInStream.cpp
index b3d00920..f3dcb85f 100755
--- a/CPP/Common/StdInStream.cpp
+++ b/CPP/Common/StdInStream.cpp
@@ -3,7 +3,10 @@
#include "StdAfx.h"
#include <tchar.h>
+
#include "StdInStream.h"
+#include "StringConvert.h"
+#include "UTFConvert.h"
#ifdef _MSC_VER
// "was declared deprecated" disabling
@@ -19,6 +22,8 @@ static const char *kIllegalCharMessage = "Illegal character in input stream";
static LPCTSTR kFileOpenMode = TEXT("r");
+extern int g_CodePage;
+
CStdInStream g_StdIn(stdin);
bool CStdInStream::Open(LPCTSTR fileName)
@@ -42,14 +47,18 @@ CStdInStream::~CStdInStream()
Close();
}
-AString CStdInStream::ScanStringUntilNewLine()
+AString CStdInStream::ScanStringUntilNewLine(bool allowEOF)
{
AString s;
for (;;)
{
int intChar = GetChar();
if (intChar == EOF)
+ {
+ if (allowEOF)
+ break;
throw kEOFMessage;
+ }
char c = char(intChar);
if (c == kIllegalChar)
throw kIllegalCharMessage;
@@ -60,6 +69,20 @@ AString CStdInStream::ScanStringUntilNewLine()
return s;
}
+UString CStdInStream::ScanUStringUntilNewLine()
+{
+ AString s = ScanStringUntilNewLine(true);
+ int codePage = g_CodePage;
+ if (codePage == -1)
+ codePage = CP_OEMCP;
+ UString dest;
+ if (codePage == CP_UTF8)
+ ConvertUTF8ToUnicode(s, dest);
+ else
+ dest = MultiByteToUnicodeString(s, (UINT)codePage);
+ return dest;
+}
+
void CStdInStream::ReadToString(AString &resultString)
{
resultString.Empty();
diff --git a/CPP/Common/StdInStream.h b/CPP/Common/StdInStream.h
index 4b08c7c5..0d182cc3 100755
--- a/CPP/Common/StdInStream.h
+++ b/CPP/Common/StdInStream.h
@@ -19,8 +19,9 @@ public:
bool Open(LPCTSTR fileName);
bool Close();
- AString ScanStringUntilNewLine();
+ AString ScanStringUntilNewLine(bool allowEOF = false);
void ReadToString(AString &resultString);
+ UString ScanUStringUntilNewLine();
bool Eof();
int GetChar();
diff --git a/CPP/Common/StdOutStream.cpp b/CPP/Common/StdOutStream.cpp
index b93e255f..061a7606 100755
--- a/CPP/Common/StdOutStream.cpp
+++ b/CPP/Common/StdOutStream.cpp
@@ -4,9 +4,10 @@
#include <tchar.h>
-#include "StdOutStream.h"
#include "IntToString.h"
+#include "StdOutStream.h"
#include "StringConvert.h"
+#include "UTFConvert.h"
#ifdef _MSC_VER
// "was declared deprecated" disabling
@@ -17,6 +18,8 @@ static const char kNewLineChar = '\n';
static const char *kFileOpenMode = "wt";
+extern int g_CodePage;
+
CStdOutStream g_StdOut(stdout);
CStdOutStream g_StdErr(stderr);
@@ -60,15 +63,23 @@ CStdOutStream & endl(CStdOutStream & outStream)
return outStream << kNewLineChar;
}
-CStdOutStream & CStdOutStream::operator<<(const char *string)
+CStdOutStream & CStdOutStream::operator<<(const char *s)
{
- fputs(string, _stream);
+ fputs(s, _stream);
return *this;
}
-CStdOutStream & CStdOutStream::operator<<(const wchar_t *string)
+CStdOutStream & CStdOutStream::operator<<(const wchar_t *s)
{
- *this << (const char *)UnicodeStringToMultiByte(string, CP_OEMCP);
+ int codePage = g_CodePage;
+ if (codePage == -1)
+ codePage = CP_OEMCP;
+ AString dest;
+ if (codePage == CP_UTF8)
+ ConvertUnicodeToUTF8(s, dest);
+ else
+ dest = UnicodeStringToMultiByte(s, (UINT)codePage);
+ *this << (const char *)dest;
return *this;
}
diff --git a/CPP/Common/Types.h b/CPP/Common/Types.h
index 4bb85410..9365b327 100755
--- a/CPP/Common/Types.h
+++ b/CPP/Common/Types.h
@@ -3,10 +3,7 @@
#ifndef __COMMON_TYPES_H
#define __COMMON_TYPES_H
-extern "C"
-{
#include "../../C/Types.h"
-}
typedef int HRes;
diff --git a/CPP/Windows/FileDevice.cpp b/CPP/Windows/FileDevice.cpp
deleted file mode 100755
index 76f1aa7a..00000000
--- a/CPP/Windows/FileDevice.cpp
+++ /dev/null
@@ -1,49 +0,0 @@
-// Windows/FileDevice.cpp
-
-#include "StdAfx.h"
-
-#include "FileDevice.h"
-
-namespace NWindows {
-namespace NFile {
-namespace NDevice {
-
-bool CFileBase::GetLengthSmart(UInt64 &length)
-{
- PARTITION_INFORMATION partInfo;
- if (GetPartitionInfo(&partInfo))
- {
- length = partInfo.PartitionLength.QuadPart;
- return true;
- }
- DISK_GEOMETRY geom;
- if (!GetGeometry(&geom))
- if (!GetCdRomGeometry(&geom))
- return false;
- length = geom.Cylinders.QuadPart * geom.TracksPerCylinder * geom.SectorsPerTrack * geom.BytesPerSector;
- return true;
-}
-
-bool CInFile::Open(LPCTSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes)
- { return Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes); }
-
-bool CInFile::Open(LPCTSTR fileName)
- { return Open(fileName, FILE_SHARE_READ, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); }
-
-#ifndef _UNICODE
-bool CInFile::Open(LPCWSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes)
- { return Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes); }
-
-bool CInFile::Open(LPCWSTR fileName)
- { return Open(fileName, FILE_SHARE_READ, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); }
-#endif
-
-bool CInFile::Read(void *data, UInt32 size, UInt32 &processedSize)
-{
- DWORD processedLoc = 0;
- bool res = BOOLToBool(::ReadFile(_handle, data, size, &processedLoc, NULL));
- processedSize = (UInt32)processedLoc;
- return res;
-}
-
-}}}
diff --git a/CPP/Windows/FileDevice.h b/CPP/Windows/FileDevice.h
deleted file mode 100755
index 0aa9bc5b..00000000
--- a/CPP/Windows/FileDevice.h
+++ /dev/null
@@ -1,123 +0,0 @@
-// Windows/FileDevice.h
-
-#ifndef __WINDOWS_FILEDEVICE_H
-#define __WINDOWS_FILEDEVICE_H
-
-#include "FileIO.h"
-#include "Defs.h"
-
-namespace NWindows {
-namespace NFile {
-namespace NDevice {
-
-typedef struct _GET_LENGTH_INFORMATION
-{
- LARGE_INTEGER Length;
-} GET_LENGTH_INFORMATION, *PGET_LENGTH_INFORMATION;
-
-#define IOCTL_DISK_GET_LENGTH_INFO CTL_CODE(IOCTL_DISK_BASE, 0x0017, METHOD_BUFFERED, FILE_READ_ACCESS)
-
-/*
-typedef struct _DISK_GEOMETRY_EX {
- DISK_GEOMETRY Geometry; // Standard disk geometry: may be faked by driver.
- LARGE_INTEGER DiskSize; // Must always be correct
- BYTE Data[1]; // Partition, Detect info
-} DISK_GEOMETRY_EX, *PDISK_GEOMETRY_EX;
-*/
-
-#define IOCTL_CDROM_BASE FILE_DEVICE_CD_ROM
-#define IOCTL_CDROM_GET_DRIVE_GEOMETRY CTL_CODE(IOCTL_CDROM_BASE, 0x0013, METHOD_BUFFERED, FILE_READ_ACCESS)
-#define IOCTL_CDROM_MEDIA_REMOVAL CTL_CODE(IOCTL_CDROM_BASE, 0x0201, METHOD_BUFFERED, FILE_READ_ACCESS)
-
-class CFileBase: public NIO::CFileBase
-{
-public:
- bool DeviceIoControl(DWORD controlCode, LPVOID inBuffer, DWORD inSize,
- LPVOID outBuffer, DWORD outSize, LPDWORD bytesReturned, LPOVERLAPPED overlapped) const
- {
- return BOOLToBool(::DeviceIoControl(_handle, controlCode, inBuffer, inSize,
- outBuffer, outSize, bytesReturned, overlapped));
- }
-
- bool DeviceIoControl(DWORD controlCode, LPVOID inBuffer,
- DWORD inSize, LPVOID outBuffer, DWORD outSize) const
- {
- DWORD ret;
- return DeviceIoControl(controlCode, inBuffer, inSize, outBuffer, outSize, &ret, 0);
- }
-
- bool DeviceIoControlIn(DWORD controlCode, LPVOID inBuffer, DWORD inSize) const
- { return DeviceIoControl(controlCode, inBuffer, inSize, NULL, 0); }
-
- bool DeviceIoControlOut(DWORD controlCode, LPVOID outBuffer, DWORD outSize) const
- { return DeviceIoControl(controlCode, NULL, 0, outBuffer, outSize); }
-
- bool GetGeometry(DISK_GEOMETRY *res) const
- { return DeviceIoControlOut(IOCTL_DISK_GET_DRIVE_GEOMETRY, res, sizeof(*res)); }
-
- bool GetCdRomGeometry(DISK_GEOMETRY *res) const
- { return DeviceIoControlOut(IOCTL_CDROM_GET_DRIVE_GEOMETRY, res, sizeof(*res)); }
-
- /*
- bool GetCdRomGeometryEx(DISK_GEOMETRY_EX *res) const
- { return DeviceIoControlOut(IOCTL_CDROM_GET_DRIVE_GEOMETRY, res, sizeof(*res)); }
- */
-
- bool CdRomLock(bool lock) const
- {
- PREVENT_MEDIA_REMOVAL rem;
- rem.PreventMediaRemoval = (BOOLEAN)(lock ? TRUE : FALSE);
- return DeviceIoControlIn(IOCTL_CDROM_MEDIA_REMOVAL, &rem, sizeof(rem));
- }
-
- bool GetLengthInfo(UInt64 &length) const
- {
- GET_LENGTH_INFORMATION lengthInfo;
- bool res = DeviceIoControlOut(IOCTL_DISK_GET_LENGTH_INFO, &lengthInfo, sizeof(lengthInfo));
- length = lengthInfo.Length.QuadPart;
- return res;
- }
-
- bool GetLengthSmart(UInt64 &length);
-
-
- /*
- bool FormatTracks(const FORMAT_PARAMETERS *formatParams,
- BAD_TRACK_NUMBER *badTrackNumbers, DWORD numBadTrackNumbers,
- DWORD &numBadTrackNumbersReturned)
- {
- DWORD ret;
- // Check params, Probabably error
- bool res = DeviceIoControl(IOCTL_DISK_FORMAT_TRACKS, badTrackNumbers, sizeof(*formatParams),
- badTrackNumbers, numBadTrackNumbers * sizeof(*badTrackNumbers), &ret, NULL);
- numBadTrackNumbersReturned = ret / sizeof(*badTrackNumbers);
- return res;
- }
- */
-
-
- bool Performance(DISK_PERFORMANCE *res)
- { return DeviceIoControlOut(IOCTL_DISK_PERFORMANCE, LPVOID(res), sizeof(*res)); }
-
- bool GetPartitionInfo(PARTITION_INFORMATION *res)
- { return DeviceIoControlOut(IOCTL_DISK_GET_PARTITION_INFO, LPVOID(res), sizeof(*res)); }
-
- bool Verify(const VERIFY_INFORMATION *verifyInformation)
- { return DeviceIoControlIn(IOCTL_DISK_VERIFY, LPVOID(verifyInformation), sizeof(*verifyInformation)); }
-};
-
-class CInFile: public CFileBase
-{
-public:
- bool Open(LPCTSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes);
- bool Open(LPCTSTR fileName);
- #ifndef _UNICODE
- bool Open(LPCWSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes);
- bool Open(LPCWSTR fileName);
- #endif
- bool Read(void *data, UInt32 size, UInt32 &processedSize);
-};
-
-}}}
-
-#endif
diff --git a/CPP/Windows/FileDir.cpp b/CPP/Windows/FileDir.cpp
index 4224d6fa..cffce7f0 100755
--- a/CPP/Windows/FileDir.cpp
+++ b/CPP/Windows/FileDir.cpp
@@ -2,14 +2,14 @@
#include "StdAfx.h"
-#include "FileDir.h"
-#include "FileName.h"
-#include "FileFind.h"
-#include "Defs.h"
#ifndef _UNICODE
#include "../Common/StringConvert.h"
#endif
+#include "FileDir.h"
+#include "FileFind.h"
+#include "FileName.h"
+
#ifndef _UNICODE
extern bool g_IsNT;
#endif
@@ -291,7 +291,7 @@ bool CreateComplexDirectory(LPCTSTR _aPathName)
if (::GetLastError() == ERROR_ALREADY_EXISTS)
{
NFind::CFileInfo fileInfo;
- if (!NFind::FindFile(pathName, fileInfo)) // For network folders
+ if (!fileInfo.Find(pathName)) // For network folders
return true;
if (!fileInfo.IsDir())
return false;
@@ -337,7 +337,7 @@ bool CreateComplexDirectory(LPCWSTR _aPathName)
if (::GetLastError() == ERROR_ALREADY_EXISTS)
{
NFind::CFileInfoW fileInfo;
- if (!NFind::FindFile(pathName, fileInfo)) // For network folders
+ if (!fileInfo.Find(pathName)) // For network folders
return true;
if (!fileInfo.IsDir())
return false;
@@ -773,18 +773,20 @@ bool CreateTempDirectory(LPCTSTR prefix, CSysString &dirName)
*/
for (;;)
{
- CTempFile tempFile;
- if (!tempFile.Create(prefix, dirName))
- return false;
- if (!::DeleteFile(dirName))
- return false;
+ {
+ CTempFile tempFile;
+ if (!tempFile.Create(prefix, dirName))
+ return false;
+ if (!tempFile.Remove())
+ return false;
+ }
/*
UINT32 randomNumber = random.Generate();
TCHAR randomNumberString[32];
_stprintf(randomNumberString, _T("%04X"), randomNumber);
dirName = prefix + randomNumberString;
*/
- if (NFind::DoesFileExist(dirName))
+ if (NFind::DoesFileOrDirExist(dirName))
continue;
if (MyCreateDirectory(dirName))
return true;
@@ -810,18 +812,20 @@ bool CreateTempDirectory(LPCWSTR prefix, UString &dirName)
*/
for (;;)
{
- CTempFileW tempFile;
- if (!tempFile.Create(prefix, dirName))
- return false;
- if (!DeleteFileAlways(dirName))
- return false;
+ {
+ CTempFileW tempFile;
+ if (!tempFile.Create(prefix, dirName))
+ return false;
+ if (!tempFile.Remove())
+ return false;
+ }
/*
UINT32 randomNumber = random.Generate();
TCHAR randomNumberString[32];
_stprintf(randomNumberString, _T("%04X"), randomNumber);
dirName = prefix + randomNumberString;
*/
- if (NFind::DoesFileExist(dirName))
+ if (NFind::DoesFileOrDirExist(dirName))
continue;
if (MyCreateDirectory(dirName))
return true;
diff --git a/CPP/Windows/FileFind.cpp b/CPP/Windows/FileFind.cpp
index f33ec961..d0cb2327 100755
--- a/CPP/Windows/FileFind.cpp
+++ b/CPP/Windows/FileFind.cpp
@@ -3,6 +3,7 @@
#include "StdAfx.h"
#include "FileFind.h"
+#include "FileIO.h"
#ifndef _UNICODE
#include "../Common/StringConvert.h"
#endif
@@ -14,6 +15,13 @@ extern bool g_IsNT;
namespace NWindows {
namespace NFile {
+#ifdef SUPPORT_DEVICE_FILE
+bool IsDeviceName(LPCTSTR n);
+#ifndef _UNICODE
+bool IsDeviceName(LPCWSTR n);
+#endif
+#endif
+
#if defined(WIN_LONG_PATH) && defined(_UNICODE)
#define WIN_LONG_PATH2
#endif
@@ -44,19 +52,26 @@ bool CFileInfoW::IsDots() const
}
#endif
-static void ConvertWIN32_FIND_DATA_To_FileInfo(const WIN32_FIND_DATA &fd, CFileInfo &fi)
-{
- fi.Attrib = fd.dwFileAttributes;
- fi.CTime = fd.ftCreationTime;
- fi.ATime = fd.ftLastAccessTime;
- fi.MTime = fd.ftLastWriteTime;
- fi.Size = (((UInt64)fd.nFileSizeHigh) << 32) + fd.nFileSizeLow;
- fi.Name = fd.cFileName;
+#define WIN_FD_TO_MY_FI(fi, fd) \
+ fi.Attrib = fd.dwFileAttributes; \
+ fi.CTime = fd.ftCreationTime; \
+ fi.ATime = fd.ftLastAccessTime; \
+ fi.MTime = fd.ftLastWriteTime; \
+ fi.Size = (((UInt64)fd.nFileSizeHigh) << 32) + fd.nFileSizeLow; \
+ fi.IsDevice = false;
+
+ /*
#ifndef _WIN32_WCE
fi.ReparseTag = fd.dwReserved0;
#else
fi.ObjectID = fd.dwOID;
#endif
+ */
+
+static void ConvertWIN32_FIND_DATA_To_FileInfo(const WIN32_FIND_DATA &fd, CFileInfo &fi)
+{
+ WIN_FD_TO_MY_FI(fi, fd);
+ fi.Name = fd.cFileName;
}
#ifndef _UNICODE
@@ -65,32 +80,14 @@ static inline UINT GetCurrentCodePage() { return ::AreFileApisANSI() ? CP_ACP :
static void ConvertWIN32_FIND_DATA_To_FileInfo(const WIN32_FIND_DATAW &fd, CFileInfoW &fi)
{
- fi.Attrib = fd.dwFileAttributes;
- fi.CTime = fd.ftCreationTime;
- fi.ATime = fd.ftLastAccessTime;
- fi.MTime = fd.ftLastWriteTime;
- fi.Size = (((UInt64)fd.nFileSizeHigh) << 32) + fd.nFileSizeLow;
+ WIN_FD_TO_MY_FI(fi, fd);
fi.Name = fd.cFileName;
- #ifndef _WIN32_WCE
- fi.ReparseTag = fd.dwReserved0;
- #else
- fi.ObjectID = fd.dwOID;
- #endif
}
static void ConvertWIN32_FIND_DATA_To_FileInfo(const WIN32_FIND_DATA &fd, CFileInfoW &fi)
{
- fi.Attrib = fd.dwFileAttributes;
- fi.CTime = fd.ftCreationTime;
- fi.ATime = fd.ftLastAccessTime;
- fi.MTime = fd.ftLastWriteTime;
- fi.Size = (((UInt64)fd.nFileSizeHigh) << 32) + fd.nFileSizeLow;
+ WIN_FD_TO_MY_FI(fi, fd);
fi.Name = GetUnicodeString(fd.cFileName, GetCurrentCodePage());
- #ifndef _WIN32_WCE
- fi.ReparseTag = fd.dwReserved0;
- #else
- fi.ObjectID = fd.dwOID;
- #endif
}
#endif
@@ -108,7 +105,7 @@ bool CFindFile::Close()
}
-bool CFindFile::FindFirst(LPCTSTR wildcard, CFileInfo &fileInfo)
+bool CFindFile::FindFirst(LPCTSTR wildcard, CFileInfo &fi)
{
if (!Close())
return false;
@@ -124,12 +121,12 @@ bool CFindFile::FindFirst(LPCTSTR wildcard, CFileInfo &fileInfo)
#endif
if (_handle == INVALID_HANDLE_VALUE)
return false;
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
return true;
}
#ifndef _UNICODE
-bool CFindFile::FindFirst(LPCWSTR wildcard, CFileInfoW &fileInfo)
+bool CFindFile::FindFirst(LPCWSTR wildcard, CFileInfoW &fi)
{
if (!Close())
return false;
@@ -146,7 +143,7 @@ bool CFindFile::FindFirst(LPCWSTR wildcard, CFileInfoW &fileInfo)
}
#endif
if (_handle != INVALID_HANDLE_VALUE)
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
}
else
{
@@ -154,95 +151,158 @@ bool CFindFile::FindFirst(LPCWSTR wildcard, CFileInfoW &fileInfo)
_handle = ::FindFirstFileA(UnicodeStringToMultiByte(wildcard,
GetCurrentCodePage()), &fd);
if (_handle != INVALID_HANDLE_VALUE)
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
}
return (_handle != INVALID_HANDLE_VALUE);
}
#endif
-bool CFindFile::FindNext(CFileInfo &fileInfo)
+bool CFindFile::FindNext(CFileInfo &fi)
{
WIN32_FIND_DATA fd;
bool result = BOOLToBool(::FindNextFile(_handle, &fd));
if (result)
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
return result;
}
#ifndef _UNICODE
-bool CFindFile::FindNext(CFileInfoW &fileInfo)
+bool CFindFile::FindNext(CFileInfoW &fi)
{
if (g_IsNT)
{
WIN32_FIND_DATAW fd;
if (!::FindNextFileW(_handle, &fd))
return false;
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
}
else
{
WIN32_FIND_DATAA fd;
if (!::FindNextFileA(_handle, &fd))
return false;
- ConvertWIN32_FIND_DATA_To_FileInfo(fd, fileInfo);
+ ConvertWIN32_FIND_DATA_To_FileInfo(fd, fi);
}
return true;
}
#endif
-bool FindFile(LPCTSTR wildcard, CFileInfo &fileInfo)
+#define MY_CLEAR_FILETIME(ft) ft.dwLowDateTime = ft.dwHighDateTime = 0;
+
+void CFileInfoBase::Clear()
+{
+ Size = 0;
+ MY_CLEAR_FILETIME(CTime);
+ MY_CLEAR_FILETIME(ATime);
+ MY_CLEAR_FILETIME(MTime);
+ Attrib = 0;
+}
+
+bool CFileInfo::Find(LPCTSTR wildcard)
{
+ #ifdef SUPPORT_DEVICE_FILE
+ if (IsDeviceName(wildcard))
+ {
+ Clear();
+ IsDevice = true;
+ NIO::CInFile inFile;
+ if (!inFile.Open(wildcard))
+ return false;
+ Name = wildcard + 4;
+ if (inFile.LengthDefined)
+ Size = inFile.Length;
+ return true;
+ }
+ #endif
CFindFile finder;
- return finder.FindFirst(wildcard, fileInfo);
+ return finder.FindFirst(wildcard, *this);
}
+
#ifndef _UNICODE
-bool FindFile(LPCWSTR wildcard, CFileInfoW &fileInfo)
+bool CFileInfoW::Find(LPCWSTR wildcard)
{
+ #ifdef SUPPORT_DEVICE_FILE
+ if (IsDeviceName(wildcard))
+ {
+ Clear();
+ IsDevice = true;
+ NIO::CInFile inFile;
+ if (!inFile.Open(wildcard))
+ return false;
+ Name = wildcard + 4;
+ if (inFile.LengthDefined)
+ Size = inFile.Length;
+ return true;
+ }
+ #endif
CFindFile finder;
- return finder.FindFirst(wildcard, fileInfo);
+ return finder.FindFirst(wildcard, *this);
}
#endif
bool DoesFileExist(LPCTSTR name)
{
- CFileInfo fileInfo;
- return FindFile(name, fileInfo);
+ CFileInfo fi;
+ return fi.Find(name) && !fi.IsDir();
+}
+
+bool DoesDirExist(LPCTSTR name)
+{
+ CFileInfo fi;
+ return fi.Find(name) && fi.IsDir();
+}
+
+bool DoesFileOrDirExist(LPCTSTR name)
+{
+ CFileInfo fi;
+ return fi.Find(name);
}
#ifndef _UNICODE
bool DoesFileExist(LPCWSTR name)
{
- CFileInfoW fileInfo;
- return FindFile(name, fileInfo);
+ CFileInfoW fi;
+ return fi.Find(name) && !fi.IsDir();
+}
+
+bool DoesDirExist(LPCWSTR name)
+{
+ CFileInfoW fi;
+ return fi.Find(name) && fi.IsDir();
+}
+bool DoesFileOrDirExist(LPCWSTR name)
+{
+ CFileInfoW fi;
+ return fi.Find(name);
}
#endif
/////////////////////////////////////
// CEnumerator
-bool CEnumerator::NextAny(CFileInfo &fileInfo)
+bool CEnumerator::NextAny(CFileInfo &fi)
{
if (_findFile.IsHandleAllocated())
- return _findFile.FindNext(fileInfo);
+ return _findFile.FindNext(fi);
else
- return _findFile.FindFirst(_wildcard, fileInfo);
+ return _findFile.FindFirst(_wildcard, fi);
}
-bool CEnumerator::Next(CFileInfo &fileInfo)
+bool CEnumerator::Next(CFileInfo &fi)
{
for (;;)
{
- if (!NextAny(fileInfo))
+ if (!NextAny(fi))
return false;
- if (!fileInfo.IsDots())
+ if (!fi.IsDots())
return true;
}
}
-bool CEnumerator::Next(CFileInfo &fileInfo, bool &found)
+bool CEnumerator::Next(CFileInfo &fi, bool &found)
{
- if (Next(fileInfo))
+ if (Next(fi))
{
found = true;
return true;
@@ -252,28 +312,28 @@ bool CEnumerator::Next(CFileInfo &fileInfo, bool &found)
}
#ifndef _UNICODE
-bool CEnumeratorW::NextAny(CFileInfoW &fileInfo)
+bool CEnumeratorW::NextAny(CFileInfoW &fi)
{
if (_findFile.IsHandleAllocated())
- return _findFile.FindNext(fileInfo);
+ return _findFile.FindNext(fi);
else
- return _findFile.FindFirst(_wildcard, fileInfo);
+ return _findFile.FindFirst(_wildcard, fi);
}
-bool CEnumeratorW::Next(CFileInfoW &fileInfo)
+bool CEnumeratorW::Next(CFileInfoW &fi)
{
for (;;)
{
- if (!NextAny(fileInfo))
+ if (!NextAny(fi))
return false;
- if (!fileInfo.IsDots())
+ if (!fi.IsDots())
return true;
}
}
-bool CEnumeratorW::Next(CFileInfoW &fileInfo, bool &found)
+bool CEnumeratorW::Next(CFileInfoW &fi, bool &found)
{
- if (Next(fileInfo))
+ if (Next(fi))
{
found = true;
return true;
diff --git a/CPP/Windows/FileFind.h b/CPP/Windows/FileFind.h
index 09b99243..4644d048 100755
--- a/CPP/Windows/FileFind.h
+++ b/CPP/Windows/FileFind.h
@@ -5,8 +5,8 @@
#include "../Common/MyString.h"
#include "../Common/Types.h"
-#include "FileName.h"
#include "Defs.h"
+#include "FileName.h"
namespace NWindows {
namespace NFile {
@@ -26,18 +26,23 @@ namespace NAttributes
class CFileInfoBase
{
bool MatchesMask(UINT32 mask) const { return ((Attrib & mask) != 0); }
+protected:
+ void Clear();
public:
UInt64 Size;
FILETIME CTime;
FILETIME ATime;
FILETIME MTime;
DWORD Attrib;
-
+ bool IsDevice;
+
+ /*
#ifndef _WIN32_WCE
UINT32 ReparseTag;
#else
DWORD ObjectID;
#endif
+ */
bool IsArchived() const { return MatchesMask(FILE_ATTRIBUTE_ARCHIVE); }
bool IsCompressed() const { return MatchesMask(FILE_ATTRIBUTE_COMPRESSED); }
@@ -53,21 +58,23 @@ public:
bool IsTemporary() const { return MatchesMask(FILE_ATTRIBUTE_TEMPORARY); }
};
-class CFileInfo: public CFileInfoBase
+struct CFileInfo: public CFileInfoBase
{
-public:
CSysString Name;
+
bool IsDots() const;
+ bool Find(LPCTSTR wildcard);
};
#ifdef _UNICODE
typedef CFileInfo CFileInfoW;
#else
-class CFileInfoW: public CFileInfoBase
+struct CFileInfoW: public CFileInfoBase
{
-public:
UString Name;
+
bool IsDots() const;
+ bool Find(LPCWSTR wildcard);
};
#endif
@@ -88,12 +95,13 @@ public:
bool Close();
};
-bool FindFile(LPCTSTR wildcard, CFileInfo &fileInfo);
-
bool DoesFileExist(LPCTSTR name);
+bool DoesDirExist(LPCTSTR name);
+bool DoesFileOrDirExist(LPCTSTR name);
#ifndef _UNICODE
-bool FindFile(LPCWSTR wildcard, CFileInfoW &fileInfo);
bool DoesFileExist(LPCWSTR name);
+bool DoesDirExist(LPCWSTR name);
+bool DoesFileOrDirExist(LPCWSTR name);
#endif
class CEnumerator
diff --git a/CPP/Windows/FileIO.cpp b/CPP/Windows/FileIO.cpp
index 5646d0a3..7279ea15 100755
--- a/CPP/Windows/FileIO.cpp
+++ b/CPP/Windows/FileIO.cpp
@@ -3,8 +3,8 @@
#include "StdAfx.h"
#include "FileIO.h"
-#include "Defs.h"
-#ifdef WIN_LONG_PATH
+
+#if defined(WIN_LONG_PATH) || defined(SUPPORT_DEVICE_FILE)
#include "../Common/MyString.h"
#endif
#ifndef _UNICODE
@@ -18,6 +18,40 @@ extern bool g_IsNT;
namespace NWindows {
namespace NFile {
+#ifdef SUPPORT_DEVICE_FILE
+bool IsDeviceName(LPCTSTR n)
+{
+ if (n[0] != '\\' || n[1] != '\\' || n[2] != '.' || n[3] != '\\')
+ return false;
+ int len = (int)MyStringLen(n);
+ if (len == 6 && n[5] == ':')
+ return true;
+ if (len < 18 || len > 22 || memcmp(n + 4, TEXT("PhysicalDrive"), 13 * sizeof(TCHAR)) != 0)
+ return false;
+ for (int i = 17; i < len; i++)
+ if (n[i] < '0' || n[i] > '9')
+ return false;
+ return true;
+}
+
+#ifndef _UNICODE
+bool IsDeviceName(LPCWSTR n)
+{
+ if (n[0] != '\\' || n[1] != '\\' || n[2] != '.' || n[3] != '\\')
+ return false;
+ int len = (int)wcslen(n);
+ if (len == 6 && n[5] == ':')
+ return true;
+ if (len < 18 || len > 22 || wcsncmp(n + 4, L"PhysicalDrive", 13) != 0)
+ return false;
+ for (int i = 17; i < len; i++)
+ if (n[i] < '0' || n[i] > '9')
+ return false;
+ return true;
+}
+#endif
+#endif
+
#if defined(WIN_LONG_PATH) && defined(_UNICODE)
#define WIN_LONG_PATH2
#endif
@@ -78,6 +112,9 @@ bool CFileBase::Create(LPCTSTR fileName, DWORD desiredAccess,
flagsAndAttributes, (HANDLE)NULL);
}
#endif
+ #ifdef SUPPORT_DEVICE_FILE
+ IsDeviceFile = false;
+ #endif
return (_handle != INVALID_HANDLE_VALUE);
}
@@ -103,6 +140,9 @@ bool CFileBase::Create(LPCWSTR fileName, DWORD desiredAccess,
flagsAndAttributes, (HANDLE)NULL);
}
#endif
+ #ifdef SUPPORT_DEVICE_FILE
+ IsDeviceFile = false;
+ #endif
return (_handle != INVALID_HANDLE_VALUE);
}
#endif
@@ -124,6 +164,14 @@ bool CFileBase::GetPosition(UInt64 &position) const
bool CFileBase::GetLength(UInt64 &length) const
{
+ #ifdef SUPPORT_DEVICE_FILE
+ if (IsDeviceFile && LengthDefined)
+ {
+ length = Length;
+ return true;
+ }
+ #endif
+
DWORD sizeHigh;
DWORD sizeLow = ::GetFileSize(_handle, &sizeHigh);
if (sizeLow == 0xFFFFFFFF)
@@ -135,6 +183,14 @@ bool CFileBase::GetLength(UInt64 &length) const
bool CFileBase::Seek(Int64 distanceToMove, DWORD moveMethod, UInt64 &newPosition) const
{
+ #ifdef SUPPORT_DEVICE_FILE
+ if (IsDeviceFile && LengthDefined && moveMethod == FILE_END)
+ {
+ distanceToMove += Length;
+ moveMethod = FILE_BEGIN;
+ }
+ #endif
+
LARGE_INTEGER value;
value.QuadPart = distanceToMove;
value.LowPart = ::SetFilePointer(_handle, value.LowPart, &value.HighPart, moveMethod);
@@ -166,7 +222,7 @@ bool CFileBase::GetFileInformation(CByHandleFileInfo &fileInfo) const
BY_HANDLE_FILE_INFORMATION winFileInfo;
if (!::GetFileInformationByHandle(_handle, &winFileInfo))
return false;
- fileInfo.Attributes = winFileInfo.dwFileAttributes;
+ fileInfo.Attrib = winFileInfo.dwFileAttributes;
fileInfo.CTime = winFileInfo.ftCreationTime;
fileInfo.ATime = winFileInfo.ftLastAccessTime;
fileInfo.MTime = winFileInfo.ftLastWriteTime;
@@ -180,8 +236,45 @@ bool CFileBase::GetFileInformation(CByHandleFileInfo &fileInfo) const
/////////////////////////
// CInFile
+#ifdef SUPPORT_DEVICE_FILE
+void CInFile::GetDeviceLength()
+{
+ if (_handle != INVALID_HANDLE_VALUE && IsDeviceFile)
+ {
+ PARTITION_INFORMATION partInfo;
+ LengthDefined = true;
+ Length = 0;
+
+ if (GetPartitionInfo(&partInfo))
+ Length = partInfo.PartitionLength.QuadPart;
+ else
+ {
+ DISK_GEOMETRY geom;
+ if (!GetGeometry(&geom))
+ if (!GetCdRomGeometry(&geom))
+ LengthDefined = false;
+ if (LengthDefined)
+ Length = geom.Cylinders.QuadPart * geom.TracksPerCylinder * geom.SectorsPerTrack * geom.BytesPerSector;
+ }
+ // SeekToBegin();
+ }
+}
+
+// ((desiredAccess & (FILE_WRITE_DATA | FILE_APPEND_DATA | GENERIC_WRITE)) == 0 &&
+
+#define MY_DEVICE_EXTRA_CODE \
+ IsDeviceFile = IsDeviceName(fileName); \
+ GetDeviceLength();
+#else
+#define MY_DEVICE_EXTRA_CODE
+#endif
+
bool CInFile::Open(LPCTSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes)
- { return Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes); }
+{
+ bool res = Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes);
+ MY_DEVICE_EXTRA_CODE
+ return res;
+}
bool CInFile::OpenShared(LPCTSTR fileName, bool shareForWrite)
{ return Open(fileName, FILE_SHARE_READ | (shareForWrite ? FILE_SHARE_WRITE : 0), OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); }
@@ -191,7 +284,11 @@ bool CInFile::Open(LPCTSTR fileName)
#ifndef _UNICODE
bool CInFile::Open(LPCWSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes)
- { return Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes); }
+{
+ bool res = Create(fileName, GENERIC_READ, shareMode, creationDisposition, flagsAndAttributes);
+ MY_DEVICE_EXTRA_CODE
+ return res;
+}
bool CInFile::OpenShared(LPCWSTR fileName, bool shareForWrite)
{ return Open(fileName, FILE_SHARE_READ | (shareForWrite ? FILE_SHARE_WRITE : 0), OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL); }
@@ -211,16 +308,21 @@ bool CInFile::Open(LPCWSTR fileName)
static UInt32 kChunkSizeMax = (1 << 22);
-bool CInFile::ReadPart(void *data, UInt32 size, UInt32 &processedSize)
+bool CInFile::Read1(void *data, UInt32 size, UInt32 &processedSize)
{
- if (size > kChunkSizeMax)
- size = kChunkSizeMax;
DWORD processedLoc = 0;
bool res = BOOLToBool(::ReadFile(_handle, data, size, &processedLoc, NULL));
processedSize = (UInt32)processedLoc;
return res;
}
+bool CInFile::ReadPart(void *data, UInt32 size, UInt32 &processedSize)
+{
+ if (size > kChunkSizeMax)
+ size = kChunkSizeMax;
+ return Read1(data, size, processedSize);
+}
+
bool CInFile::Read(void *data, UInt32 size, UInt32 &processedSize)
{
processedSize = 0;
diff --git a/CPP/Windows/FileIO.h b/CPP/Windows/FileIO.h
index f1e600ec..4e7308c7 100755
--- a/CPP/Windows/FileIO.h
+++ b/CPP/Windows/FileIO.h
@@ -5,26 +5,29 @@
#include "../Common/Types.h"
+#include "Defs.h"
+
namespace NWindows {
namespace NFile {
namespace NIO {
struct CByHandleFileInfo
{
- DWORD Attributes;
+ DWORD Attrib;
FILETIME CTime;
FILETIME ATime;
FILETIME MTime;
- DWORD VolumeSerialNumber;
- UInt64 Size;
- DWORD NumberOfLinks;
- UInt64 FileIndex;
+ DWORD VolumeSerialNumber;
+ UInt64 Size;
+ DWORD NumberOfLinks;
+ UInt64 FileIndex;
};
class CFileBase
{
protected:
HANDLE _handle;
+
bool Create(LPCTSTR fileName, DWORD desiredAccess,
DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes);
#ifndef _UNICODE
@@ -33,7 +36,13 @@ protected:
#endif
public:
- CFileBase(): _handle(INVALID_HANDLE_VALUE){};
+ #ifdef SUPPORT_DEVICE_FILE
+ bool IsDeviceFile;
+ bool LengthDefined;
+ UInt64 Length;
+ #endif
+
+ CFileBase(): _handle(INVALID_HANDLE_VALUE) {};
~CFileBase();
bool Close();
@@ -49,8 +58,42 @@ public:
bool GetFileInformation(CByHandleFileInfo &fileInfo) const;
};
+#define IOCTL_CDROM_BASE FILE_DEVICE_CD_ROM
+#define IOCTL_CDROM_GET_DRIVE_GEOMETRY CTL_CODE(IOCTL_CDROM_BASE, 0x0013, METHOD_BUFFERED, FILE_READ_ACCESS)
+#define IOCTL_CDROM_MEDIA_REMOVAL CTL_CODE(IOCTL_CDROM_BASE, 0x0201, METHOD_BUFFERED, FILE_READ_ACCESS)
+
class CInFile: public CFileBase
{
+ #ifdef SUPPORT_DEVICE_FILE
+ bool DeviceIoControl(DWORD controlCode, LPVOID inBuffer, DWORD inSize,
+ LPVOID outBuffer, DWORD outSize, LPDWORD bytesReturned, LPOVERLAPPED overlapped) const
+ {
+ return BOOLToBool(::DeviceIoControl(_handle, controlCode, inBuffer, inSize,
+ outBuffer, outSize, bytesReturned, overlapped));
+ }
+
+ bool DeviceIoControl(DWORD controlCode, LPVOID inBuffer,
+ DWORD inSize, LPVOID outBuffer, DWORD outSize) const
+ {
+ DWORD ret;
+ return DeviceIoControl(controlCode, inBuffer, inSize, outBuffer, outSize, &ret, 0);
+ }
+
+ bool DeviceIoControlOut(DWORD controlCode, LPVOID outBuffer, DWORD outSize) const
+ { return DeviceIoControl(controlCode, NULL, 0, outBuffer, outSize); }
+
+ bool GetGeometry(DISK_GEOMETRY *res) const
+ { return DeviceIoControlOut(IOCTL_DISK_GET_DRIVE_GEOMETRY, res, sizeof(*res)); }
+
+ bool GetCdRomGeometry(DISK_GEOMETRY *res) const
+ { return DeviceIoControlOut(IOCTL_CDROM_GET_DRIVE_GEOMETRY, res, sizeof(*res)); }
+
+ bool GetPartitionInfo(PARTITION_INFORMATION *res)
+ { return DeviceIoControlOut(IOCTL_DISK_GET_PARTITION_INFO, LPVOID(res), sizeof(*res)); }
+
+ void GetDeviceLength();
+ #endif
+
public:
bool Open(LPCTSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes);
bool OpenShared(LPCTSTR fileName, bool shareForWrite);
@@ -60,15 +103,14 @@ public:
bool OpenShared(LPCWSTR fileName, bool shareForWrite);
bool Open(LPCWSTR fileName);
#endif
+ bool Read1(void *data, UInt32 size, UInt32 &processedSize);
bool ReadPart(void *data, UInt32 size, UInt32 &processedSize);
bool Read(void *data, UInt32 size, UInt32 &processedSize);
};
class COutFile: public CFileBase
{
- // DWORD m_CreationDisposition;
public:
- // COutFile(): m_CreationDisposition(CREATE_NEW){};
bool Open(LPCTSTR fileName, DWORD shareMode, DWORD creationDisposition, DWORD flagsAndAttributes);
bool Open(LPCTSTR fileName, DWORD creationDisposition);
bool Create(LPCTSTR fileName, bool createAlways);
@@ -79,13 +121,6 @@ public:
bool Create(LPCWSTR fileName, bool createAlways);
#endif
- /*
- void SetOpenCreationDisposition(DWORD creationDisposition)
- { m_CreationDisposition = creationDisposition; }
- void SetOpenCreationDispositionCreateAlways()
- { m_CreationDisposition = CREATE_ALWAYS; }
- */
-
bool SetTime(const FILETIME *cTime, const FILETIME *aTime, const FILETIME *mTime);
bool SetMTime(const FILETIME *mTime);
bool WritePart(const void *data, UInt32 size, UInt32 &processedSize);
diff --git a/CPP/Windows/PropVariant.cpp b/CPP/Windows/PropVariant.cpp
index ae2e6cd1..1db6c236 100755
--- a/CPP/Windows/PropVariant.cpp
+++ b/CPP/Windows/PropVariant.cpp
@@ -65,6 +65,26 @@ CPropVariant& CPropVariant::operator=(LPCOLESTR lpszSrc)
}
+CPropVariant& CPropVariant::operator=(const char *s)
+{
+ InternalClear();
+ vt = VT_BSTR;
+ wReserved1 = 0;
+ UINT len = (UINT)strlen(s);
+ bstrVal = ::SysAllocStringByteLen(0, (UINT)len * sizeof(OLECHAR));
+ if (bstrVal == NULL)
+ {
+ vt = VT_ERROR;
+ scode = E_OUTOFMEMORY;
+ }
+ else
+ {
+ for (UINT i = 0; i <= len; i++)
+ bstrVal[i] = s[i];
+ }
+ return *this;
+}
+
CPropVariant& CPropVariant::operator=(bool bSrc)
{
if (vt != VT_BOOL)
diff --git a/CPP/Windows/PropVariant.h b/CPP/Windows/PropVariant.h
index d44215f0..5552bbe2 100755
--- a/CPP/Windows/PropVariant.h
+++ b/CPP/Windows/PropVariant.h
@@ -31,6 +31,7 @@ public:
CPropVariant& operator=(const PROPVARIANT& varSrc);
CPropVariant& operator=(BSTR bstrSrc);
CPropVariant& operator=(LPCOLESTR lpszSrc);
+ CPropVariant& operator=(const char *s);
CPropVariant& operator=(bool bSrc);
CPropVariant& operator=(UInt32 value);
CPropVariant& operator=(UInt64 value);
diff --git a/CPP/Windows/Security.cpp b/CPP/Windows/Security.cpp
index bb8c3a9a..6f5bcad3 100755
--- a/CPP/Windows/Security.cpp
+++ b/CPP/Windows/Security.cpp
@@ -121,8 +121,7 @@ bool AddLockMemoryPrivilege()
!= 0)
return false;
LSA_UNICODE_STRING userRights;
- wchar_t s[128];
- wcscpy(s, MY__SE_LOCK_MEMORY_NAME);
+ wchar_t s[128] = MY__SE_LOCK_MEMORY_NAME;
SetLsaString(s, &userRights);
WCHAR userName[256 + 2];
DWORD size = 256;
diff --git a/CPP/Windows/Synchronization.h b/CPP/Windows/Synchronization.h
index 8d34ae9d..54fcf952 100755
--- a/CPP/Windows/Synchronization.h
+++ b/CPP/Windows/Synchronization.h
@@ -3,12 +3,9 @@
#ifndef __WINDOWS_SYNCHRONIZATION_H
#define __WINDOWS_SYNCHRONIZATION_H
-#include "Defs.h"
-
-extern "C"
-{
#include "../../C/Threads.h"
-}
+
+#include "Defs.h"
#ifdef _WIN32
#include "Handle.h"
@@ -23,7 +20,7 @@ protected:
::CEvent _object;
public:
bool IsCreated() { return Event_IsCreated(&_object) != 0; }
- operator HANDLE() { return _object.handle; }
+ operator HANDLE() { return _object; }
CBaseEvent() { Event_Construct(&_object); }
~CBaseEvent() { Close(); }
WRes Close() { return Event_Close(&_object); }
@@ -31,16 +28,16 @@ public:
WRes Create(bool manualReset, bool initiallyOwn, LPCTSTR name = NULL,
LPSECURITY_ATTRIBUTES securityAttributes = NULL)
{
- _object.handle = ::CreateEvent(securityAttributes, BoolToBOOL(manualReset),
+ _object = ::CreateEvent(securityAttributes, BoolToBOOL(manualReset),
BoolToBOOL(initiallyOwn), name);
- if (_object.handle != 0)
+ if (_object != 0)
return 0;
return ::GetLastError();
}
WRes Open(DWORD desiredAccess, bool inheritHandle, LPCTSTR name)
{
- _object.handle = ::OpenEvent(desiredAccess, BoolToBOOL(inheritHandle), name);
- if (_object.handle != 0)
+ _object = ::OpenEvent(desiredAccess, BoolToBOOL(inheritHandle), name);
+ if (_object != 0)
return 0;
return ::GetLastError();
}
@@ -134,7 +131,7 @@ public:
CSemaphore() { Semaphore_Construct(&_object); }
~CSemaphore() { Close(); }
WRes Close() { return Semaphore_Close(&_object); }
- operator HANDLE() { return _object.handle; }
+ operator HANDLE() { return _object; }
WRes Create(UInt32 initiallyCount, UInt32 maxCount)
{
return Semaphore_Create(&_object, initiallyCount, maxCount);
diff --git a/CPP/Windows/Thread.h b/CPP/Windows/Thread.h
index 39104f4a..16a509d4 100755
--- a/CPP/Windows/Thread.h
+++ b/CPP/Windows/Thread.h
@@ -3,12 +3,9 @@
#ifndef __WINDOWS_THREAD_H
#define __WINDOWS_THREAD_H
-#include "Defs.h"
-
-extern "C"
-{
#include "../../C/Threads.h"
-}
+
+#include "Defs.h"
namespace NWindows {
@@ -25,14 +22,14 @@ public:
WRes Wait() { return Thread_Wait(&thread); }
#ifdef _WIN32
- operator HANDLE() { return thread.handle; }
- void Attach(HANDLE handle) { thread.handle = handle; }
- HANDLE Detach() { HANDLE h = thread.handle; thread.handle = NULL; return h; }
- DWORD Resume() { return ::ResumeThread(thread.handle); }
- DWORD Suspend() { return ::SuspendThread(thread.handle); }
- bool Terminate(DWORD exitCode) { return BOOLToBool(::TerminateThread(thread.handle, exitCode)); }
- int GetPriority() { return ::GetThreadPriority(thread.handle); }
- bool SetPriority(int priority) { return BOOLToBool(::SetThreadPriority(thread.handle, priority)); }
+ operator HANDLE() { return thread; }
+ void Attach(HANDLE handle) { thread = handle; }
+ HANDLE Detach() { HANDLE h = thread; thread = NULL; return h; }
+ DWORD Resume() { return ::ResumeThread(thread); }
+ DWORD Suspend() { return ::SuspendThread(thread); }
+ bool Terminate(DWORD exitCode) { return BOOLToBool(::TerminateThread(thread, exitCode)); }
+ int GetPriority() { return ::GetThreadPriority(thread); }
+ bool SetPriority(int priority) { return BOOLToBool(::SetThreadPriority(thread, priority)); }
#endif
};