2007-07-26 14:45:49 +02:00
|
|
|
|
; Loading of 7z archives was ported from 7z sources (file 7zip\Archive\7z\7zIn.cpp).
|
|
|
|
|
; The version 7-Zip 4.42 was used.
|
|
|
|
|
; 7-Zip is copyright (C) 1999-2006 Igor Pavlov.
|
|
|
|
|
; Assembler version as KFar plugin has been written by diamond, 2007.
|
|
|
|
|
|
|
|
|
|
virtual at 0
|
|
|
|
|
file_in_7z:
|
|
|
|
|
.fullname dd ? ; pointer to cp866 string
|
|
|
|
|
.name dd ?
|
|
|
|
|
.namelen dd ?
|
|
|
|
|
.bIsDirectory db ?
|
|
|
|
|
.bPseudoFolder db ?
|
|
|
|
|
rb 2
|
|
|
|
|
.parent dd ? ; pointer to parent directory record
|
|
|
|
|
.subfolders dd ? ; head of L2-list of subfolders [for folders]
|
|
|
|
|
.subfolders.end dd ?
|
|
|
|
|
.subfiles dd ? ; head of L2-list of files [for folders]
|
|
|
|
|
.subfiles.end dd ?
|
|
|
|
|
.NumSubItems dd ?
|
|
|
|
|
.next dd ? ; next item of list of subfolders or files
|
|
|
|
|
.prev dd ? ; previous item of list of subfolders or files
|
2007-09-20 18:20:58 +02:00
|
|
|
|
.stamp dd ?
|
2007-07-26 14:45:49 +02:00
|
|
|
|
.attr dd ?
|
|
|
|
|
.FileCRC dd ?
|
|
|
|
|
.startPos dq ?
|
|
|
|
|
.CreationTime dq ?
|
|
|
|
|
.LastAccessTime dq ?
|
|
|
|
|
.LastWriteTime dq ?
|
|
|
|
|
.UnPackSize dq ?
|
|
|
|
|
.folder dd ?
|
|
|
|
|
.folder_index dd ?
|
|
|
|
|
.folderStart dq ?
|
|
|
|
|
.bAttrDefined db ?
|
|
|
|
|
.bStartPosDefined db ?
|
|
|
|
|
.bCRCDefined db ?
|
|
|
|
|
.bCreationTimeDefined db ?
|
|
|
|
|
.bLastAccessTimeDefined db ?
|
|
|
|
|
.bLastWriteTimeDefined db ?
|
|
|
|
|
.bHasStream db ?
|
|
|
|
|
.bAnti db ?
|
|
|
|
|
.size = $
|
|
|
|
|
end virtual
|
|
|
|
|
|
|
|
|
|
virtual at 0
|
|
|
|
|
handle_7z:
|
|
|
|
|
.type dd ?
|
|
|
|
|
.root.subfolders dd ?
|
|
|
|
|
.root.subfolders.end dd ?
|
|
|
|
|
.root.subfiles dd ?
|
|
|
|
|
.root.subfiles.end dd ?
|
|
|
|
|
.root.NumSubItems dd ?
|
|
|
|
|
.curdir dd ?
|
|
|
|
|
.NumFiles dd ?
|
|
|
|
|
.names_buf dd ?
|
|
|
|
|
.host dd ?
|
|
|
|
|
.host_datetime rd 6
|
|
|
|
|
; streams info
|
|
|
|
|
.numPackStreams dd ?
|
|
|
|
|
.packSizes dd ?
|
|
|
|
|
.numFolders dd ?
|
|
|
|
|
.unpackCRCsDefined dd ?
|
|
|
|
|
.unpackCRCs dd ?
|
|
|
|
|
.folders dd ?
|
|
|
|
|
.last_folder dd ?
|
|
|
|
|
.last_pos dq ?
|
|
|
|
|
.last_context dd ?
|
|
|
|
|
.last_main_stream dd ?
|
|
|
|
|
.password_len dd ? ; -1 if no password defined; in characters
|
|
|
|
|
.password rw password_maxlen
|
|
|
|
|
.basesize = $
|
|
|
|
|
; .size = .basesize + .NumFiles * file_in_7z.size
|
|
|
|
|
end virtual
|
|
|
|
|
|
|
|
|
|
iglobal
|
|
|
|
|
align 4
|
|
|
|
|
empty_7z_handle:
|
|
|
|
|
dd type_7z
|
|
|
|
|
dd 0,0,0,0,0,0
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
kEnd = 0
|
|
|
|
|
kHeader = 1
|
|
|
|
|
kArchiveProperties = 2
|
|
|
|
|
kAdditionalStreamsInfo = 3
|
|
|
|
|
kMainStreamsInfo = 4
|
|
|
|
|
kFilesInfo = 5
|
|
|
|
|
kPackInfo = 6
|
|
|
|
|
kUnPackInfo = 7
|
|
|
|
|
kSubStreamsInfo = 8
|
|
|
|
|
kSize = 9
|
|
|
|
|
kCRC = 10
|
|
|
|
|
kFolder = 11
|
|
|
|
|
kCodersUnPackSize = 12
|
|
|
|
|
kNumUnPackStream = 13
|
|
|
|
|
kEmptyStream = 14
|
|
|
|
|
kEmptyFile = 15
|
|
|
|
|
kAnti = 16
|
|
|
|
|
kName = 17
|
|
|
|
|
kCreationTime = 18
|
|
|
|
|
kLastAccessTime = 19
|
|
|
|
|
kLastWriteTime = 20
|
|
|
|
|
kWinAttributes = 21
|
|
|
|
|
kComment = 22
|
|
|
|
|
kEncodedHeader = 23
|
|
|
|
|
kStartPos = 24
|
|
|
|
|
|
|
|
|
|
_7z.ReadByte:
|
|
|
|
|
cmp edi, [bufend]
|
|
|
|
|
jae return.err
|
|
|
|
|
mov al, [edi]
|
|
|
|
|
inc edi
|
|
|
|
|
ret
|
|
|
|
|
_7z.ReadWord:
|
|
|
|
|
add edi, 2
|
|
|
|
|
cmp edi, [bufend]
|
|
|
|
|
ja return.err
|
|
|
|
|
mov ax, [edi-2]
|
|
|
|
|
ret
|
|
|
|
|
_7z.ReadDword:
|
|
|
|
|
add edi, 4
|
|
|
|
|
cmp edi, [bufend]
|
|
|
|
|
ja return.err
|
|
|
|
|
mov eax, [edi-4]
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.SkipSize:
|
|
|
|
|
test edx, edx
|
|
|
|
|
jnz return.err
|
|
|
|
|
add edi, eax
|
|
|
|
|
jc return.err
|
|
|
|
|
cmp edi, [bufend]
|
|
|
|
|
ja return.err
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.ReadNumber:
|
|
|
|
|
xor eax, eax
|
|
|
|
|
push eax
|
|
|
|
|
push eax
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
push ecx
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
@@:
|
|
|
|
|
add al, al
|
|
|
|
|
jnc @f
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
shr eax, cl
|
|
|
|
|
shr eax, 1
|
|
|
|
|
jz @f
|
|
|
|
|
mov [esp+4+ecx], al
|
|
|
|
|
@@:
|
|
|
|
|
jecxz .ret
|
|
|
|
|
push edx
|
|
|
|
|
xor edx, edx
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
mov [esp+8+edx], al
|
|
|
|
|
inc edx
|
|
|
|
|
loop @b
|
|
|
|
|
pop edx
|
|
|
|
|
.ret:
|
|
|
|
|
pop ecx
|
|
|
|
|
pop eax
|
|
|
|
|
pop edx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.ReadNum:
|
|
|
|
|
push edx
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
test edx, edx
|
|
|
|
|
jnz return.err
|
|
|
|
|
test eax, eax
|
|
|
|
|
js return.err
|
|
|
|
|
pop edx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
open_7z:
|
|
|
|
|
; CInArchive::ReadDatabase()
|
|
|
|
|
cmp byte [esi+6], 0 ; major version must be 0
|
|
|
|
|
; minor version does not be checked ([byte +7]=2 for now)
|
|
|
|
|
jz @f
|
|
|
|
|
xor eax, eax
|
|
|
|
|
ret
|
|
|
|
|
@@:
|
|
|
|
|
and [hOut], 0
|
|
|
|
|
and [_7z.FreeSubStreams], 0
|
|
|
|
|
and [_7z.tmpVector], 0
|
|
|
|
|
push esi
|
|
|
|
|
add esi, 12
|
|
|
|
|
mov ecx, 20
|
|
|
|
|
call crc
|
|
|
|
|
pop esi
|
|
|
|
|
cmp eax, [esi+8]
|
|
|
|
|
jnz .header_crc_error
|
|
|
|
|
cmp dword [esi+24], 0
|
|
|
|
|
jnz .header_error
|
|
|
|
|
mov edi, buffer
|
|
|
|
|
mov ecx, [esi+20]
|
|
|
|
|
mov [bufsize], ecx
|
|
|
|
|
test ecx, ecx
|
|
|
|
|
jnz .notempty
|
|
|
|
|
mov eax, empty_7z_handle
|
|
|
|
|
push ebp
|
|
|
|
|
call [close]
|
|
|
|
|
ret
|
|
|
|
|
.notempty:
|
|
|
|
|
cmp ecx, 1024
|
|
|
|
|
jbe @f
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .reterr
|
|
|
|
|
mov edi, eax
|
|
|
|
|
@@:
|
|
|
|
|
mov [bufptr], edi
|
|
|
|
|
lea eax, [edi+ecx]
|
|
|
|
|
mov [bufend], eax
|
|
|
|
|
mov eax, [esi+12]
|
|
|
|
|
mov edx, [esi+16]
|
|
|
|
|
add eax, 20h ; end of main header
|
|
|
|
|
adc edx, 0
|
|
|
|
|
push edx
|
|
|
|
|
push eax
|
|
|
|
|
push 0
|
|
|
|
|
push ebp
|
|
|
|
|
call [seek]
|
|
|
|
|
push ecx
|
|
|
|
|
push edi
|
|
|
|
|
push ebp
|
|
|
|
|
call [read]
|
|
|
|
|
cmp eax, ecx
|
|
|
|
|
jnz .header_error
|
|
|
|
|
push esi
|
|
|
|
|
mov esi, edi
|
|
|
|
|
call crc
|
|
|
|
|
pop esi
|
|
|
|
|
cmp eax, [esi+28]
|
|
|
|
|
jz .header_ok
|
|
|
|
|
.header_crc_error:
|
|
|
|
|
.header_error:
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push HeaderError_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
.clear:
|
|
|
|
|
mov ecx, [_7z.tmpVector]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [hOut]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call _7z.CloseHandle
|
|
|
|
|
@@:
|
|
|
|
|
mov ebx, [_7z.dataVectorSize]
|
|
|
|
|
test ebx, ebx
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadAndDecodePackedStreams.free2
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.FreeSubStreams]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [bufptr]
|
|
|
|
|
cmp ecx, buffer
|
|
|
|
|
jz .reterr
|
|
|
|
|
call [pgfree]
|
|
|
|
|
.reterr:
|
|
|
|
|
or eax, -1
|
|
|
|
|
ret
|
|
|
|
|
.header_ok:
|
|
|
|
|
mov [_esp], esp
|
|
|
|
|
mov [inStream], ebp
|
|
|
|
|
.loop:
|
|
|
|
|
mov [error_proc], .header_error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
and [_7z.dataVectorSize], 0
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
cmp eax, kHeader
|
|
|
|
|
jz .found_header
|
|
|
|
|
cmp eax, kEncodedHeader
|
|
|
|
|
jnz .header_error
|
|
|
|
|
call _7z.ReadAndDecodePackedStreams
|
|
|
|
|
cmp [_7z.StreamsInfo.numFolders], 0
|
|
|
|
|
jz .free_empty
|
|
|
|
|
cmp [_7z.StreamsInfo.numFolders], 1
|
|
|
|
|
jnz return.err
|
|
|
|
|
mov ecx, [bufptr]
|
|
|
|
|
cmp ecx, buffer
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov edi, [_7z.unpbuf+4]
|
|
|
|
|
mov [bufptr], edi
|
|
|
|
|
mov ecx, [_7z.unpbuf]
|
|
|
|
|
add ecx, edi
|
|
|
|
|
mov [bufend], ecx
|
|
|
|
|
mov [error_proc], .header_error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
and [_7z.dataVectorSize], 0
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
cmp eax, kHeader
|
|
|
|
|
jz .found_header
|
|
|
|
|
jmp return.err
|
|
|
|
|
.free_empty:
|
|
|
|
|
mov ecx, [bufptr]
|
|
|
|
|
cmp ecx, buffer
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
push [inStream]
|
|
|
|
|
call [close]
|
|
|
|
|
mov eax, empty_7z_handle
|
|
|
|
|
ret
|
|
|
|
|
.found_header:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
cmp eax, kArchiveProperties
|
|
|
|
|
jnz .no_archive_props
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
.no_archive_props:
|
|
|
|
|
cmp eax, kAdditionalStreamsInfo
|
|
|
|
|
jnz .no_additional_streams
|
|
|
|
|
call _7z.ReadAndDecodePackedStreams
|
|
|
|
|
mov eax, [_7z.unpacked]
|
|
|
|
|
mov [_7z.dataVector], eax
|
|
|
|
|
mov eax, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
mov [_7z.dataVectorSize], eax
|
|
|
|
|
mov [error_proc], .header_error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
.no_additional_streams:
|
|
|
|
|
cmp eax, kMainStreamsInfo
|
|
|
|
|
jnz return.err
|
|
|
|
|
call _7z.ReadStreamsInfo
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jnz .notempty2
|
|
|
|
|
.empty2:
|
|
|
|
|
mov ebx, [_7z.dataVectorSize]
|
|
|
|
|
test ebx, ebx
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadAndDecodePackedStreams.free2
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.FreeSubStreams]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [bufptr]
|
|
|
|
|
cmp ecx, buffer
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
push [inStream]
|
|
|
|
|
call [close]
|
|
|
|
|
mov eax, empty_7z_handle
|
|
|
|
|
ret
|
|
|
|
|
.notempty2:
|
|
|
|
|
cmp eax, kFilesInfo
|
|
|
|
|
jnz return.err
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .empty2
|
|
|
|
|
mov ebx, eax ; number of files in archive
|
|
|
|
|
imul ecx, ebx, file_in_7z.size
|
|
|
|
|
add ecx, handle_7z.basesize
|
|
|
|
|
mov [hOut.allocated], ecx
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [hOut], eax
|
|
|
|
|
mov [eax+handle_7z.type], type_7z
|
|
|
|
|
mov [eax+handle_7z.NumFiles], ebx
|
|
|
|
|
push edi
|
|
|
|
|
lea edi, [eax+handle_7z.numPackStreams]
|
|
|
|
|
mov esi, _7z.StreamsInfo
|
|
|
|
|
mov ecx, 6
|
|
|
|
|
rep movsd
|
|
|
|
|
or [eax+handle_7z.password_len], -1
|
|
|
|
|
or [eax+handle_7z.last_folder], -1
|
|
|
|
|
mov [eax+handle_7z.last_context], ecx
|
|
|
|
|
mov [eax+handle_7z.names_buf], ecx
|
|
|
|
|
mov [eax+handle_7z.host], ecx
|
|
|
|
|
cmp [bPasswordDefined], cl
|
|
|
|
|
jz @f
|
|
|
|
|
mov ecx, [password_size]
|
|
|
|
|
mov [eax+handle_7z.password_len], ecx
|
|
|
|
|
lea edi, [eax+handle_7z.password]
|
|
|
|
|
mov esi, password_unicode
|
|
|
|
|
shr ecx, 1
|
|
|
|
|
rep movsd
|
|
|
|
|
adc ecx, ecx
|
|
|
|
|
rep movsw
|
|
|
|
|
@@:
|
|
|
|
|
lea edi, [eax+handle_7z.basesize]
|
|
|
|
|
imul ecx, ebx, file_in_7z.size/4
|
|
|
|
|
xor eax, eax
|
|
|
|
|
rep stosd
|
|
|
|
|
pop edi
|
|
|
|
|
mov eax, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
mov [_7z.FreeSubStreams], eax
|
|
|
|
|
mov [error_proc], .header_error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
shl ecx, 2
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
push edi
|
|
|
|
|
mov edi, eax
|
|
|
|
|
mov [_7z.tmpVector], eax
|
|
|
|
|
add eax, ebx
|
|
|
|
|
mov [_7z.emptyStreams], eax
|
|
|
|
|
add eax, ebx
|
|
|
|
|
mov [_7z.emptyFiles], eax
|
|
|
|
|
add eax, ebx
|
|
|
|
|
mov [_7z.antiFiles], eax
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
xor eax, eax
|
|
|
|
|
rep stosd
|
|
|
|
|
pop edi
|
|
|
|
|
mov [_7z.numEmptyStreams], eax
|
|
|
|
|
.parse_header:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .parse_header_done
|
|
|
|
|
mov ecx, eax ; ecx = type
|
|
|
|
|
call _7z.ReadNum ; eax = size
|
|
|
|
|
cmp ecx, kName
|
|
|
|
|
jz .parse_names
|
|
|
|
|
cmp ecx, kWinAttributes
|
|
|
|
|
jz .parse_winAttr
|
|
|
|
|
cmp ecx, kStartPos
|
|
|
|
|
jz .parse_startPos
|
|
|
|
|
cmp ecx, kEmptyStream
|
|
|
|
|
jz .parse_emptyStream
|
|
|
|
|
cmp ecx, kEmptyFile
|
|
|
|
|
jz .parse_emptyFile
|
|
|
|
|
cmp ecx, kAnti
|
|
|
|
|
jz .parse_anti
|
|
|
|
|
cmp ecx, kCreationTime
|
|
|
|
|
jz .parse_time
|
|
|
|
|
cmp ecx, kLastWriteTime
|
|
|
|
|
jz .parse_time
|
|
|
|
|
cmp ecx, kLastAccessTime
|
|
|
|
|
jz .parse_time
|
|
|
|
|
xor edx, edx
|
|
|
|
|
call _7z.SkipSize
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_names:
|
|
|
|
|
push eax
|
|
|
|
|
call _7z.SwitchStream
|
|
|
|
|
pop eax
|
|
|
|
|
jz @f
|
|
|
|
|
mov eax, [bufend]
|
|
|
|
|
sub eax, edi
|
|
|
|
|
@@:
|
|
|
|
|
shr eax, 1 ; size of ANSI string is a half of size of UNICODE string
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov ebp, eax
|
|
|
|
|
mov esi, [hOut]
|
|
|
|
|
mov [esi+handle_7z.names_buf], eax
|
|
|
|
|
add eax, ecx
|
|
|
|
|
push eax ; remember limit
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
add esi, handle_7z.basesize + file_in_7z.fullname
|
|
|
|
|
mov [bWasWarning], 0
|
|
|
|
|
.parse_names_loop:
|
|
|
|
|
mov [esi], ebp
|
|
|
|
|
add esi, file_in_7z.size
|
|
|
|
|
.parse_names_loop_int:
|
|
|
|
|
cmp ebp, [esp]
|
|
|
|
|
jae return.err
|
|
|
|
|
call _7z.ReadWord
|
|
|
|
|
; UNICODE char -> cp866 char
|
|
|
|
|
cmp ax, 0x80
|
|
|
|
|
jb .id
|
|
|
|
|
cmp ax, 0x401
|
|
|
|
|
jz .yo1
|
|
|
|
|
cmp ax, 0x451
|
|
|
|
|
jz .yo2
|
|
|
|
|
cmp ax, 0x410
|
|
|
|
|
jb .unk
|
|
|
|
|
cmp ax, 0x440
|
|
|
|
|
jb .rus1
|
|
|
|
|
cmp ax, 0x450
|
|
|
|
|
jb .rus2
|
|
|
|
|
.unk:
|
|
|
|
|
cmp [bWasWarning], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aEncodingProblem_str_ptr
|
|
|
|
|
push 3
|
|
|
|
|
push aEncodingProblem
|
|
|
|
|
call [Message]
|
|
|
|
|
inc [bWasWarning]
|
|
|
|
|
@@:
|
|
|
|
|
mov al, '_'
|
|
|
|
|
jmp .id
|
|
|
|
|
.yo1:
|
|
|
|
|
mov al, '<27>'
|
|
|
|
|
jmp .id
|
|
|
|
|
.yo2:
|
|
|
|
|
mov al, '<27>'
|
|
|
|
|
jmp .id
|
|
|
|
|
.rus1:
|
|
|
|
|
; 0x410-0x43F -> 0x80-0xAF
|
|
|
|
|
add al, 0x70
|
|
|
|
|
jmp .id
|
|
|
|
|
.rus2:
|
|
|
|
|
; 0x440-0x44F -> 0xE0-0xEF
|
|
|
|
|
add al, 0xA0
|
|
|
|
|
.id:
|
|
|
|
|
mov [ebp], al
|
|
|
|
|
inc ebp
|
|
|
|
|
test al, al
|
|
|
|
|
jnz .parse_names_loop_int
|
|
|
|
|
loop .parse_names_loop
|
|
|
|
|
pop eax
|
|
|
|
|
call _7z.UnswitchStream
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_winAttr:
|
|
|
|
|
mov edx, [_7z.tmpVector]
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
mov ebx, edx
|
|
|
|
|
call _7z.ReadBoolVector2
|
|
|
|
|
pop ebx
|
|
|
|
|
call _7z.SwitchStream
|
|
|
|
|
mov esi, [hOut]
|
|
|
|
|
add esi, handle_7z.basesize
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
.winAttrLoop:
|
|
|
|
|
mov al, [edx]
|
|
|
|
|
inc edx
|
|
|
|
|
mov [esi+file_in_7z.bAttrDefined], al
|
|
|
|
|
test al, al
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
mov [esi+file_in_7z.attr], eax
|
|
|
|
|
@@:
|
|
|
|
|
add esi, file_in_7z.size
|
|
|
|
|
loop .winAttrLoop
|
|
|
|
|
call _7z.UnswitchStream
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_startPos:
|
|
|
|
|
mov edx, [_7z.tmpVector]
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
mov ebx, edx
|
|
|
|
|
call _7z.ReadBoolVector2
|
|
|
|
|
pop ebx
|
|
|
|
|
call _7z.SwitchStream
|
|
|
|
|
mov esi, [hOut]
|
|
|
|
|
add esi, handle_7z.basesize
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
.startPosLoop:
|
|
|
|
|
mov al, [edx]
|
|
|
|
|
inc edx
|
|
|
|
|
mov [esi+file_in_7z.bStartPosDefined], al
|
|
|
|
|
test al, al
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
mov dword [esi+file_in_7z.startPos], eax
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
mov dword [esi+file_in_7z.startPos+4], eax
|
|
|
|
|
@@:
|
|
|
|
|
add esi, file_in_7z.size
|
|
|
|
|
loop .startPosLoop
|
|
|
|
|
call _7z.UnswitchStream
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_emptyStream:
|
|
|
|
|
mov edx, [_7z.emptyStreams]
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
mov ebx, edx
|
|
|
|
|
call _7z.ReadBoolVector
|
|
|
|
|
pop ebx
|
|
|
|
|
and [_7z.numEmptyStreams], 0
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
.emptyStrLoop:
|
|
|
|
|
cmp byte [edx], 0
|
|
|
|
|
jz @f
|
|
|
|
|
inc [_7z.numEmptyStreams]
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
loop .emptyStrLoop
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_emptyFile:
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, [_7z.numEmptyStreams]
|
|
|
|
|
mov ebx, [_7z.emptyFiles]
|
|
|
|
|
call _7z.ReadBoolVector
|
|
|
|
|
pop ebx
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_anti:
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, [_7z.numEmptyStreams]
|
|
|
|
|
mov ebx, [_7z.antiFiles]
|
|
|
|
|
call _7z.ReadBoolVector
|
|
|
|
|
pop ebx
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_time:
|
|
|
|
|
push ecx
|
|
|
|
|
push ebx
|
|
|
|
|
mov ecx, ebx
|
|
|
|
|
mov ebx, [_7z.tmpVector]
|
|
|
|
|
call _7z.ReadBoolVector2
|
|
|
|
|
pop ebx
|
|
|
|
|
call _7z.SwitchStream
|
|
|
|
|
mov esi, [hOut]
|
|
|
|
|
add esi, handle_7z.basesize
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.timeLoop:
|
|
|
|
|
mov eax, [_7z.tmpVector]
|
|
|
|
|
mov al, [eax+ecx]
|
|
|
|
|
pop edx
|
|
|
|
|
push edx
|
|
|
|
|
mov [esi + file_in_7z.bCreationTimeDefined + edx - kCreationTime], al
|
|
|
|
|
test al, al
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
push eax
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
mov edx, eax
|
|
|
|
|
pop eax
|
|
|
|
|
push edi
|
|
|
|
|
mov edi, [esp+4]
|
|
|
|
|
lea edi, [esi + file_in_7z.CreationTime + (edi-kCreationTime)*8]
|
|
|
|
|
call ntfs_datetime_to_bdfe
|
|
|
|
|
pop edi
|
|
|
|
|
@@:
|
|
|
|
|
add esi, file_in_7z.size
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, ebx
|
|
|
|
|
jb .timeLoop
|
|
|
|
|
call _7z.UnswitchStream
|
|
|
|
|
pop eax
|
|
|
|
|
jmp .parse_header
|
|
|
|
|
.parse_header_done:
|
|
|
|
|
xor ecx, ecx ; index in emptyFiles
|
|
|
|
|
xor edx, edx ; index in subStreams
|
|
|
|
|
xor ebp, ebp ; index in files
|
|
|
|
|
mov esi, [hOut]
|
|
|
|
|
add esi, handle_7z.basesize
|
|
|
|
|
.filesLoop:
|
|
|
|
|
mov eax, [_7z.emptyStreams]
|
|
|
|
|
mov al, [eax+ebp]
|
|
|
|
|
xor al, 1
|
|
|
|
|
mov [esi+file_in_7z.bHasStream], al
|
|
|
|
|
jz .nostream
|
|
|
|
|
mov [esi+file_in_7z.bIsDirectory], 0
|
|
|
|
|
mov [esi+file_in_7z.bAnti], 0
|
|
|
|
|
mov eax, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
push dword [eax+edx*8]
|
|
|
|
|
pop dword [esi+file_in_7z.UnPackSize]
|
|
|
|
|
push dword [eax+edx*8+4]
|
|
|
|
|
pop dword [esi+file_in_7z.UnPackSize+4]
|
|
|
|
|
mov eax, [_7z.StreamsInfo.SubStreamsCRCsDefined]
|
|
|
|
|
mov al, [eax+edx]
|
|
|
|
|
mov [esi+file_in_7z.bCRCDefined], al
|
|
|
|
|
test al, al
|
|
|
|
|
jz @f
|
|
|
|
|
mov eax, [_7z.StreamsInfo.SubStreamsCRCs]
|
|
|
|
|
mov eax, [eax+edx*4]
|
|
|
|
|
mov [esi+file_in_7z.FileCRC], eax
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
jmp .filesCont
|
|
|
|
|
.nostream:
|
|
|
|
|
mov eax, [_7z.emptyFiles]
|
|
|
|
|
cmp byte [eax+ecx], 0
|
|
|
|
|
setz [esi+file_in_7z.bIsDirectory]
|
|
|
|
|
mov eax, [_7z.antiFiles]
|
|
|
|
|
cmp byte [eax+ecx], 0
|
|
|
|
|
setnz [esi+file_in_7z.bAnti]
|
|
|
|
|
and dword [esi+file_in_7z.UnPackSize], 0
|
|
|
|
|
and dword [esi+file_in_7z.UnPackSize+4], 0
|
|
|
|
|
mov [esi+file_in_7z.bCRCDefined], 0
|
|
|
|
|
inc ecx
|
|
|
|
|
.filesCont:
|
|
|
|
|
inc ebp
|
|
|
|
|
add esi, file_in_7z.size
|
|
|
|
|
dec ebx
|
|
|
|
|
jnz .filesLoop
|
|
|
|
|
mov ecx, [_7z.tmpVector]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
and [_7z.tmpVector], 0
|
|
|
|
|
mov ebx, [_7z.dataVectorSize]
|
|
|
|
|
test ebx, ebx
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadAndDecodePackedStreams.free2
|
|
|
|
|
and [_7z.dataVectorSize], 0
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.FreeSubStreams]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
and [_7z.FreeSubStreams], 0
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [bufptr]
|
|
|
|
|
cmp ecx, buffer
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
mov [bufptr], buffer
|
|
|
|
|
@@:
|
|
|
|
|
xor esi, esi ; index of folder
|
|
|
|
|
mov edi, [hOut]
|
|
|
|
|
mov ebx, [edi+handle_7z.NumFiles]
|
|
|
|
|
add edi, handle_7z.basesize ; pointer to fileinfo
|
|
|
|
|
push 0 ; start index of packed stream for folder
|
|
|
|
|
.getfoldersloop0:
|
|
|
|
|
xor edx, edx ; index in folder
|
|
|
|
|
push edx edx ; position in folder
|
|
|
|
|
.getfoldersloop:
|
|
|
|
|
dec ebx
|
|
|
|
|
js .getfoldersdone
|
|
|
|
|
cmp [edi+file_in_7z.bHasStream], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
test edx, edx
|
|
|
|
|
jz .nofolder
|
|
|
|
|
@@:
|
|
|
|
|
test edx, edx
|
|
|
|
|
jnz .notfirst
|
|
|
|
|
; skip empty folders
|
|
|
|
|
@@:
|
|
|
|
|
mov eax, [hOut]
|
|
|
|
|
cmp esi, [eax+handle_7z.numFolders]
|
|
|
|
|
jae return.err
|
|
|
|
|
mov eax, [eax+handle_7z.folders]
|
|
|
|
|
mov eax, [eax+esi*4]
|
|
|
|
|
cmp edx, [eax+_7z.StreamsInfo.numUnPackStreams]
|
|
|
|
|
jb @f
|
|
|
|
|
inc esi
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
.notfirst:
|
|
|
|
|
mov [edi+file_in_7z.folder], esi
|
|
|
|
|
mov [edi+file_in_7z.folder_index], edx
|
|
|
|
|
mov eax, [esp]
|
|
|
|
|
mov dword [edi+file_in_7z.folderStart], eax
|
|
|
|
|
mov eax, [esp+4]
|
|
|
|
|
mov dword [edi+file_in_7z.folderStart+4], eax
|
|
|
|
|
mov ecx, dword [edi+file_in_7z.UnPackSize]
|
|
|
|
|
add [esp], ecx
|
|
|
|
|
mov ecx, dword [edi+file_in_7z.UnPackSize+4]
|
|
|
|
|
adc [esp+4], ecx
|
|
|
|
|
add edi, file_in_7z.size
|
|
|
|
|
inc edx
|
|
|
|
|
mov eax, [hOut]
|
|
|
|
|
mov eax, [eax+handle_7z.folders]
|
|
|
|
|
mov eax, [eax+esi*4]
|
|
|
|
|
cmp edx, [eax+_7z.StreamsInfo.numUnPackStreams]
|
|
|
|
|
jb .getfoldersloop
|
|
|
|
|
inc esi
|
|
|
|
|
pop edx edx
|
|
|
|
|
jmp .getfoldersloop0
|
|
|
|
|
.nofolder:
|
|
|
|
|
push -1
|
|
|
|
|
pop eax
|
|
|
|
|
mov [edi+file_in_7z.folder], eax
|
|
|
|
|
mov [edi+file_in_7z.folder_index], eax
|
|
|
|
|
mov dword [edi+file_in_7z.folderStart], eax
|
|
|
|
|
mov dword [edi+file_in_7z.folderStart+4], eax
|
|
|
|
|
add edi, file_in_7z.size
|
|
|
|
|
jmp .getfoldersloop
|
|
|
|
|
.getfoldersdone:
|
|
|
|
|
pop eax eax eax
|
|
|
|
|
mov ebp, [hOut]
|
|
|
|
|
mov esi, [ebp+handle_7z.folders]
|
|
|
|
|
xor ebx, ebx
|
|
|
|
|
cmp ebx, [ebp+handle_7z.numFolders]
|
|
|
|
|
jae .getoffsdone
|
|
|
|
|
.getoffsloop:
|
|
|
|
|
lodsd
|
|
|
|
|
test ebx, ebx
|
|
|
|
|
jnz .getoffs2
|
|
|
|
|
mov edx, dword [_7z.StreamsInfo.dataOffset]
|
|
|
|
|
mov dword [eax+_7z.StreamsInfo.packOffset], edx
|
|
|
|
|
mov edx, dword [_7z.StreamsInfo.dataOffset+4]
|
|
|
|
|
mov dword [eax+_7z.StreamsInfo.packOffset+4], edx
|
|
|
|
|
jmp .getoffscont
|
|
|
|
|
.getoffs2:
|
|
|
|
|
mov ecx, [esi-8]
|
|
|
|
|
mov edx, dword [ecx+_7z.StreamsInfo.packOffset]
|
|
|
|
|
mov dword [eax+_7z.StreamsInfo.packOffset], edx
|
|
|
|
|
mov edx, dword [ecx+_7z.StreamsInfo.packOffset+4]
|
|
|
|
|
mov dword [eax+_7z.StreamsInfo.packOffset+4], edx
|
|
|
|
|
mov edi, [ecx+_7z.StreamsInfo.startPackedStream]
|
|
|
|
|
mov ecx, [ecx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
push ecx
|
|
|
|
|
add ecx, edi
|
|
|
|
|
cmp ecx, [ebp+handle_7z.numPackStreams]
|
|
|
|
|
ja return.err
|
|
|
|
|
pop ecx
|
|
|
|
|
shl edi, 3
|
|
|
|
|
add edi, [ebp+handle_7z.packSizes]
|
|
|
|
|
@@:
|
|
|
|
|
dec ecx
|
|
|
|
|
js @f
|
|
|
|
|
mov edx, [edi]
|
|
|
|
|
add dword [eax+_7z.StreamsInfo.packOffset], edx
|
|
|
|
|
mov edx, [edi+4]
|
|
|
|
|
adc dword [eax+_7z.StreamsInfo.packOffset+4], edx
|
|
|
|
|
add edi, 8
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
.getoffscont:
|
|
|
|
|
inc ebx
|
|
|
|
|
cmp ebx, [ebp+handle_7z.numFolders]
|
|
|
|
|
jb .getoffsloop
|
|
|
|
|
.getoffsdone:
|
|
|
|
|
mov edx, [hOut]
|
|
|
|
|
mov ebx, [edx+handle_7z.NumFiles]
|
|
|
|
|
lea edi, [edx+handle_7z.root.subfolders]
|
|
|
|
|
add edx, handle_7z.basesize
|
|
|
|
|
push file_in_7z.size
|
|
|
|
|
call init_file_links
|
|
|
|
|
mov eax, [hOut]
|
|
|
|
|
and [eax+handle_7z.curdir], 0 ; set root directory
|
|
|
|
|
mov esi, [inStream]
|
|
|
|
|
mov [eax+handle_7z.host], esi
|
|
|
|
|
lea edi, [eax+handle_7z.host_datetime]
|
2007-09-20 18:20:58 +02:00
|
|
|
|
mov esi, [esp+12]
|
2007-07-26 14:45:49 +02:00
|
|
|
|
add esi, 8
|
|
|
|
|
mov ecx, 6
|
|
|
|
|
rep movsd
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.CloseHandle:
|
|
|
|
|
mov esi, ecx
|
|
|
|
|
push [esi+handle_7z.host]
|
|
|
|
|
call [close]
|
|
|
|
|
mov ecx, [esi+handle_7z.packSizes]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
mov ecx, [esi+handle_7z.folders]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
mov ecx, [esi+handle_7z.names_buf]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
mov ecx, [esi+handle_7z.last_context]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, esi
|
|
|
|
|
call [pgfree]
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
close_7z:
|
|
|
|
|
mov ecx, [esp+4]
|
|
|
|
|
cmp ecx, empty_7z_handle
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.CloseHandle
|
|
|
|
|
@@:
|
|
|
|
|
ret 4
|
|
|
|
|
|
|
|
|
|
uglobal
|
|
|
|
|
align 4
|
|
|
|
|
_7z.unpacked dd ?
|
|
|
|
|
_7z.unpbuf rd 2*8
|
|
|
|
|
_7z.CurInStream dd ?
|
|
|
|
|
_7z.dataVector dd ?
|
|
|
|
|
_7z.dataVectorSize dd ?
|
|
|
|
|
_7z.FreeSubStreams dd ?
|
|
|
|
|
_7z.tmpVector dd ?
|
|
|
|
|
_7z.emptyStreams dd ?
|
|
|
|
|
_7z.numEmptyStreams dd ?
|
|
|
|
|
_7z.emptyFiles dd ?
|
|
|
|
|
_7z.antiFiles dd ?
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
_7z.ReadAndDecodePackedStreams:
|
|
|
|
|
call _7z.ReadStreamsInfo
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
test ecx, ecx
|
|
|
|
|
jz .ret2
|
|
|
|
|
push ecx
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
and [_7z.StreamsInfo.SubStreamsSizes], 0
|
|
|
|
|
@@:
|
|
|
|
|
pop ecx
|
|
|
|
|
mov eax, _7z.unpbuf
|
|
|
|
|
cmp ecx, 8
|
|
|
|
|
jbe .1
|
|
|
|
|
shl ecx, 3
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov esi, eax
|
|
|
|
|
@@:
|
|
|
|
|
and dword [esi], 0
|
|
|
|
|
add esi, 4
|
|
|
|
|
sub ecx, 4
|
|
|
|
|
jnz @b
|
|
|
|
|
.1:
|
|
|
|
|
mov [_7z.unpacked], eax
|
|
|
|
|
mov esi, eax
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov [_7z.CurInStream], ecx
|
|
|
|
|
mov [error_proc], .error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
.loop:
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov ebx, [eax+ecx*4]
|
|
|
|
|
call _7z.GetUnPackSize
|
|
|
|
|
test edx, edx
|
|
|
|
|
jnz return.err
|
|
|
|
|
test eax, eax
|
|
|
|
|
js return.err
|
|
|
|
|
push ecx
|
|
|
|
|
mov [esi], eax
|
|
|
|
|
mov [_7z.decode.outBufferSize], eax
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.err
|
|
|
|
|
mov [esi+4], eax
|
|
|
|
|
mov [_7z.decode.outBufferPtr], eax
|
|
|
|
|
push esi
|
|
|
|
|
call _7z.decode
|
|
|
|
|
pop esi
|
|
|
|
|
pop ecx
|
|
|
|
|
push ecx
|
|
|
|
|
mov eax, [_7z.StreamsInfo.unpackCRCsDefined]
|
|
|
|
|
cmp byte [eax+ecx], 0
|
|
|
|
|
jz @f
|
|
|
|
|
push esi
|
|
|
|
|
mov ecx, [esi]
|
|
|
|
|
mov esi, [esi+4]
|
|
|
|
|
call crc
|
|
|
|
|
pop esi
|
|
|
|
|
pop ecx
|
|
|
|
|
push ecx
|
|
|
|
|
mov edx, [_7z.StreamsInfo.unpackCRCs]
|
|
|
|
|
cmp [edx+ecx*4], eax
|
|
|
|
|
jnz return.err
|
|
|
|
|
@@:
|
|
|
|
|
add esi, 8
|
|
|
|
|
pop ecx
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jb .loop
|
|
|
|
|
.ret:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.folders]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
mov [error_proc], .error2
|
|
|
|
|
mov [clear_proc], .clear2
|
|
|
|
|
.ret2:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.packSizes]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
.error:
|
|
|
|
|
call .free
|
|
|
|
|
jmp _7z.ReadStreamsInfo.error
|
|
|
|
|
.clear:
|
|
|
|
|
call .free
|
|
|
|
|
jmp _7z.ReadStreamsInfo.clear
|
|
|
|
|
.error2:
|
|
|
|
|
call .free
|
|
|
|
|
jmp open_7z.header_error
|
|
|
|
|
.clear2:
|
|
|
|
|
call .free
|
|
|
|
|
jmp open_7z.clear
|
|
|
|
|
.free:
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
.free2:
|
|
|
|
|
dec ebx
|
|
|
|
|
js @f
|
|
|
|
|
mov ecx, [_7z.unpacked]
|
|
|
|
|
mov ecx, [ecx+ebx*8+4]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
jmp .free2
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.unpacked]
|
|
|
|
|
cmp ecx, _7z.unpbuf
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.GetUnPackSize:
|
|
|
|
|
xor edx, edx
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.numOutStreams]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .ret
|
|
|
|
|
.scan:
|
|
|
|
|
dec eax
|
|
|
|
|
js return.err
|
|
|
|
|
push ecx
|
|
|
|
|
mov ecx, [ebx+_7z.StreamsInfo.numBindPairs]
|
|
|
|
|
mov edx, [ebx+_7z.StreamsInfo.bindPairs]
|
|
|
|
|
@@:
|
|
|
|
|
add edx, 8
|
|
|
|
|
dec ecx
|
|
|
|
|
js .found
|
|
|
|
|
cmp [edx-4], eax
|
|
|
|
|
jnz @b
|
|
|
|
|
pop ecx
|
|
|
|
|
jmp .scan
|
|
|
|
|
.found:
|
|
|
|
|
mov [ebx+_7z.StreamsInfo.mainOutStream], eax
|
|
|
|
|
mov ecx, [ebx+_7z.StreamsInfo.unpackSizes]
|
|
|
|
|
mov edx, [ecx+eax*8+4]
|
|
|
|
|
mov eax, [ecx+eax*8]
|
|
|
|
|
pop ecx
|
|
|
|
|
.ret:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
uglobal
|
|
|
|
|
align 4
|
|
|
|
|
_7z.StreamsInfo:
|
|
|
|
|
.numPackStreams dd ?
|
|
|
|
|
.packSizes dd ? ; 8 bytes per item
|
|
|
|
|
.numFolders dd ?
|
|
|
|
|
.unpackCRCsDefined dd ?
|
|
|
|
|
.unpackCRCs dd ?
|
|
|
|
|
.folders dd ?
|
|
|
|
|
.folders.size dd ?
|
|
|
|
|
.folders.alloc dd ?
|
|
|
|
|
.dataOffset dq ?
|
|
|
|
|
.packCRCsDefined dd ? ; 1 byte per item
|
|
|
|
|
.packCRCs dd ? ; 4 bytes per item
|
|
|
|
|
virtual at 0
|
|
|
|
|
.numCoders dd ?
|
|
|
|
|
.bindPairs dd ?
|
|
|
|
|
.numBindPairs dd ?
|
|
|
|
|
.packedStreams dd ?
|
|
|
|
|
.numPackedStreams dd ?
|
|
|
|
|
.startPackedStream dd ?
|
|
|
|
|
.numOutStreams dd ?
|
|
|
|
|
.unpackSizes dd ?
|
|
|
|
|
.mainOutStream dd ?
|
|
|
|
|
.numUnPackStreams dd ?
|
|
|
|
|
.packOffset dq ?
|
|
|
|
|
.fsz = $
|
|
|
|
|
end virtual
|
|
|
|
|
.numSubStreams dd ?
|
|
|
|
|
.SubStreamsSizes dd ?
|
|
|
|
|
.SubStreamsCRCsDefined dd ?
|
|
|
|
|
.SubStreamsCRCs dd ?
|
|
|
|
|
.tmpSubStreamsCRCsDefined dd ?
|
|
|
|
|
.tmpSubStreamsCRCs dd ?
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
_7z.SkipData:
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
call _7z.SkipSize
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.WaitAttribute:
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
cmp eax, ecx
|
|
|
|
|
jz @f
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.err
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
jmp _7z.WaitAttribute
|
|
|
|
|
@@:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.ReadBoolVector2:
|
|
|
|
|
; in: ebx->vector, ecx=size
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
test al, al
|
|
|
|
|
jz _7z.ReadBoolVector
|
|
|
|
|
push ebx ecx
|
|
|
|
|
jecxz .ret
|
|
|
|
|
@@:
|
|
|
|
|
mov byte [ebx], 1
|
|
|
|
|
inc ebx
|
|
|
|
|
loop @b
|
|
|
|
|
.ret:
|
|
|
|
|
pop ecx ebx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.ReadBoolVector:
|
|
|
|
|
push ebx ecx
|
|
|
|
|
jecxz .ret
|
|
|
|
|
xor eax, eax
|
|
|
|
|
.1:
|
|
|
|
|
add al, al
|
|
|
|
|
jnz @f
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
stc
|
|
|
|
|
adc al, al
|
|
|
|
|
@@:
|
|
|
|
|
setc byte [ebx]
|
|
|
|
|
inc ebx
|
|
|
|
|
loop .1
|
|
|
|
|
.ret:
|
|
|
|
|
pop ecx ebx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.ReadHashDigests:
|
|
|
|
|
; in: ebx->bool vector, esi->crc, ecx=size
|
|
|
|
|
call _7z.ReadBoolVector2
|
|
|
|
|
jecxz .ret
|
|
|
|
|
.1:
|
|
|
|
|
xor eax, eax
|
|
|
|
|
cmp byte [ebx], al
|
|
|
|
|
jz @f
|
|
|
|
|
call _7z.ReadDword
|
|
|
|
|
@@:
|
|
|
|
|
mov [esi], eax
|
|
|
|
|
add esi, 4
|
|
|
|
|
inc ebx
|
|
|
|
|
loop .1
|
|
|
|
|
.ret:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
uglobal
|
|
|
|
|
_7z.saved_edi dd ?
|
|
|
|
|
_7z.saved_edi_end dd ?
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
_7z.SwitchStream:
|
|
|
|
|
mov eax, [bufend]
|
|
|
|
|
mov [_7z.saved_edi_end], eax
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
test al, al
|
|
|
|
|
jnz @f
|
|
|
|
|
ret
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [_7z.saved_edi], edi
|
|
|
|
|
cmp eax, [_7z.dataVectorSize]
|
|
|
|
|
jae return.err
|
|
|
|
|
shl eax, 3
|
|
|
|
|
add eax, [_7z.dataVector]
|
|
|
|
|
mov edi, [eax+4]
|
|
|
|
|
mov eax, [eax]
|
|
|
|
|
add eax, edi
|
|
|
|
|
mov [bufend], eax
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
_7z.UnswitchStream:
|
|
|
|
|
mov eax, [_7z.saved_edi_end]
|
|
|
|
|
cmp eax, [bufend]
|
|
|
|
|
jnz @f
|
|
|
|
|
ret
|
|
|
|
|
@@:
|
|
|
|
|
mov [bufend], eax
|
|
|
|
|
mov edi, [_7z.saved_edi]
|
|
|
|
|
@@:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
; 6 <EFBFBD>ணࠬ<EFBFBD><EFBFBD><EFBFBD>⮢ <EFBFBD><EFBFBD>⠫<EFBFBD><EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>,
|
|
|
|
|
; <EFBFBD><EFBFBD><EFBFBD><EFBFBD> <EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD> <EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <EFBFBD> 㬠, <EFBFBD> <EFBFBD><EFBFBD> <EFBFBD><EFBFBD>⠫<EFBFBD><EFBFBD><EFBFBD> 5.
|
|
|
|
|
|
|
|
|
|
_7z.ReadStreamsInfo:
|
|
|
|
|
xor eax, eax
|
|
|
|
|
mov [_7z.StreamsInfo.numPackStreams], eax
|
|
|
|
|
mov [_7z.StreamsInfo.packSizes], eax
|
|
|
|
|
mov [_7z.StreamsInfo.numFolders], eax
|
|
|
|
|
mov [_7z.StreamsInfo.folders], eax
|
|
|
|
|
mov [_7z.StreamsInfo.numSubStreams], eax
|
|
|
|
|
mov [_7z.StreamsInfo.SubStreamsSizes], eax
|
|
|
|
|
mov [_7z.StreamsInfo.tmpSubStreamsCRCsDefined], eax
|
|
|
|
|
mov [error_proc], .error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
.mainloop:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz @b
|
|
|
|
|
cmp eax, kSubStreamsInfo
|
|
|
|
|
jz .SubStreamsInfo
|
|
|
|
|
cmp eax, kUnPackInfo
|
|
|
|
|
jz .UnpackInfo
|
|
|
|
|
cmp eax, kPackInfo
|
|
|
|
|
jnz return.err
|
|
|
|
|
|
|
|
|
|
.PackInfo:
|
|
|
|
|
cmp [_7z.StreamsInfo.numPackStreams], 0
|
|
|
|
|
jnz return.err
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
add eax, 0x20
|
|
|
|
|
adc edx, 0
|
|
|
|
|
mov dword [_7z.StreamsInfo.dataOffset], eax
|
|
|
|
|
mov dword [_7z.StreamsInfo.dataOffset+4], edx
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [_7z.StreamsInfo.numPackStreams], eax
|
|
|
|
|
mov ecx, kSize
|
|
|
|
|
call _7z.WaitAttribute
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numPackStreams]
|
|
|
|
|
imul ecx, 8+1+4
|
|
|
|
|
jecxz .nostreams1
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [_7z.StreamsInfo.packSizes], eax
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numPackStreams]
|
|
|
|
|
push eax
|
|
|
|
|
lea eax, [eax+ecx*8]
|
|
|
|
|
mov [_7z.StreamsInfo.packCRCsDefined], eax
|
|
|
|
|
mov ebx, eax
|
|
|
|
|
add eax, ecx
|
|
|
|
|
mov [_7z.StreamsInfo.packCRCs], eax
|
|
|
|
|
@@:
|
|
|
|
|
mov byte [ebx], 0
|
|
|
|
|
inc ebx
|
|
|
|
|
loop @b
|
|
|
|
|
pop eax
|
|
|
|
|
.nostreams1:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numPackStreams]
|
|
|
|
|
jecxz .noloop1
|
|
|
|
|
mov esi, eax
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
mov [esi], eax
|
|
|
|
|
mov [esi+4], edx
|
|
|
|
|
add esi, 8
|
|
|
|
|
loop @b
|
|
|
|
|
.noloop1:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .mainloop
|
|
|
|
|
cmp eax, kCRC
|
|
|
|
|
jz .packInfo.crc
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
jmp .noloop1
|
|
|
|
|
.packInfo.crc:
|
|
|
|
|
mov esi, [_7z.StreamsInfo.packCRCs]
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.packCRCsDefined]
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numPackStreams]
|
|
|
|
|
call _7z.ReadHashDigests
|
|
|
|
|
jmp .noloop1
|
|
|
|
|
|
|
|
|
|
.UnpackInfo:
|
|
|
|
|
cmp [_7z.StreamsInfo.folders], 0
|
|
|
|
|
jnz return.err
|
|
|
|
|
mov ecx, kFolder
|
|
|
|
|
call _7z.WaitAttribute
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
mov [_7z.StreamsInfo.numFolders], eax
|
|
|
|
|
call _7z.SwitchStream
|
|
|
|
|
test ecx, ecx
|
|
|
|
|
jz .nofolders
|
|
|
|
|
push ecx
|
|
|
|
|
mov ecx, 0x1000
|
|
|
|
|
and [_7z.StreamsInfo.folders.size], 0
|
|
|
|
|
mov [_7z.StreamsInfo.folders.alloc], ecx
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [_7z.StreamsInfo.folders], eax
|
|
|
|
|
pop ecx
|
|
|
|
|
lea ecx, [ecx*9]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.folderloop:
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
push [_7z.StreamsInfo.folders.size]
|
|
|
|
|
pop dword [eax+ecx*4]
|
|
|
|
|
push ebp
|
|
|
|
|
mov [_ebp], ebp
|
|
|
|
|
push ecx
|
|
|
|
|
mov ecx, _7z.StreamsInfo.fsz
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
mov ebp, eax
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.numCoders], eax
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.err
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
push ecx
|
|
|
|
|
shl ecx, 2
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
pop ecx
|
|
|
|
|
add eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
@@:
|
|
|
|
|
and dword [eax], 0
|
|
|
|
|
add eax, 4
|
|
|
|
|
loop @b
|
|
|
|
|
push 0 ; numOutStreams
|
|
|
|
|
push 0 ; numInStreams
|
|
|
|
|
; [folders] = array of pointers to coders info
|
|
|
|
|
; Format of coder info:
|
|
|
|
|
; dd NextCoder
|
|
|
|
|
; db MethodID.IDSize
|
|
|
|
|
; times IDSize db MethodID.ID
|
|
|
|
|
; dd NumInStreams
|
|
|
|
|
; dd NumOutStreams
|
|
|
|
|
; dd PropSize
|
|
|
|
|
; times PropSize db Properties
|
|
|
|
|
xor esi, esi
|
|
|
|
|
.coders_loop:
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
mov dl, al
|
|
|
|
|
and eax, 0xF
|
|
|
|
|
lea ecx, [eax+17]
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
push eax
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.folders]
|
|
|
|
|
lea ebx, [ebp+esi*4+_7z.StreamsInfo.fsz]
|
|
|
|
|
@@:
|
|
|
|
|
cmp dword [ebx], 0
|
|
|
|
|
jz @f
|
|
|
|
|
mov ebx, [ebx]
|
|
|
|
|
add ebx, ecx
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
mov [ebx], eax
|
|
|
|
|
pop ebx
|
|
|
|
|
add ebx, ecx
|
|
|
|
|
and dword [ebx], 0
|
|
|
|
|
add ebx, 4
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
and ecx, 0xF
|
|
|
|
|
mov byte [ebx], cl
|
|
|
|
|
inc ebx
|
|
|
|
|
jecxz .2
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
mov byte [ebx], al
|
|
|
|
|
inc ebx
|
|
|
|
|
loop @b
|
|
|
|
|
.2:
|
|
|
|
|
test dl, 10h
|
|
|
|
|
jnz .coder_multiple_streams
|
|
|
|
|
mov dword [ebx], 1
|
|
|
|
|
mov dword [ebx+4], 1
|
|
|
|
|
inc dword [esp]
|
|
|
|
|
inc dword [esp+4]
|
|
|
|
|
jmp @f
|
|
|
|
|
.coder_multiple_streams:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [ebx], eax
|
|
|
|
|
add dword [esp], eax
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [ebx+4], eax
|
|
|
|
|
add dword [esp+4], eax
|
|
|
|
|
; all currently defined 7z coders have 1 unpacked stream
|
|
|
|
|
; moreover, all reasonable coders have 1 unpacked stream
|
|
|
|
|
; so assume 1 output stream for unpacker - this simplifies decoding procedure
|
|
|
|
|
cmp eax, 1
|
|
|
|
|
jnz return.err
|
|
|
|
|
@@:
|
|
|
|
|
and dword [ebx+8], 0
|
|
|
|
|
add ebx, 12
|
|
|
|
|
test dl, 20h
|
|
|
|
|
jz .coder_no_properties
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .coder_no_properties
|
|
|
|
|
mov [ebx-4], eax
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
sub ebx, [_7z.StreamsInfo.folders]
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
add ebx, [_7z.StreamsInfo.folders]
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadByte
|
|
|
|
|
mov [ebx], al
|
|
|
|
|
inc ebx
|
|
|
|
|
loop @b
|
|
|
|
|
.coder_no_properties:
|
|
|
|
|
test dl, dl
|
|
|
|
|
js .coders_loop
|
|
|
|
|
inc esi
|
|
|
|
|
cmp esi, [ebp+_7z.StreamsInfo.numCoders]
|
|
|
|
|
jb .coders_loop
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.numUnPackStreams], 1
|
|
|
|
|
mov eax, [esp+4]
|
|
|
|
|
dec eax
|
|
|
|
|
js return.err
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.numBindPairs], eax
|
|
|
|
|
push eax
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
shl ecx, 3
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.bindPairs], eax
|
|
|
|
|
pop ecx
|
|
|
|
|
jecxz .noloop3
|
|
|
|
|
mov esi, eax
|
|
|
|
|
add esi, [_7z.StreamsInfo.folders]
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [esi], eax
|
|
|
|
|
cmp eax, [esp]
|
|
|
|
|
jae return.err
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [esi+4], eax
|
|
|
|
|
cmp eax, [esp+4]
|
|
|
|
|
jae return.err
|
|
|
|
|
add esi, 8
|
|
|
|
|
loop @b
|
|
|
|
|
.noloop3:
|
|
|
|
|
pop eax ; numInStreams
|
|
|
|
|
pop edx ; numOutStreams
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.numOutStreams], edx
|
|
|
|
|
sub eax, edx
|
|
|
|
|
js return.err
|
|
|
|
|
inc eax
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.numPackedStreams], eax
|
|
|
|
|
mov ecx, eax
|
|
|
|
|
push eax
|
|
|
|
|
shl ecx, 2
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.packedStreams], eax
|
|
|
|
|
pop ecx
|
|
|
|
|
mov esi, eax
|
|
|
|
|
add esi, [_7z.StreamsInfo.folders]
|
|
|
|
|
cmp ecx, 1
|
|
|
|
|
jnz .multiplePackedStreams
|
|
|
|
|
mov ebx, [ebp+_7z.StreamsInfo.bindPairs]
|
|
|
|
|
add ebx, [_7z.StreamsInfo.folders]
|
|
|
|
|
push edx
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.3:
|
|
|
|
|
push ebx
|
|
|
|
|
mov edx, [ebp+_7z.StreamsInfo.numBindPairs]
|
|
|
|
|
@@:
|
|
|
|
|
dec edx
|
|
|
|
|
js .5
|
|
|
|
|
cmp dword [ebx], ecx
|
|
|
|
|
jz .4
|
|
|
|
|
add ebx, 8
|
|
|
|
|
jmp @b
|
|
|
|
|
.4:
|
|
|
|
|
pop ebx
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp .3
|
|
|
|
|
.5:
|
|
|
|
|
pop ebx
|
|
|
|
|
pop edx
|
|
|
|
|
mov [esi], ecx
|
|
|
|
|
jmp .commonPackedStreams
|
|
|
|
|
.multiplePackedStreams:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov [esi], eax
|
|
|
|
|
add esi, 4
|
|
|
|
|
loop .multiplePackedStreams
|
|
|
|
|
.commonPackedStreams:
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
shl ecx, 3
|
|
|
|
|
sub ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
call .folders_alloc
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.unpackSizes], eax
|
|
|
|
|
pop ecx
|
|
|
|
|
xor edx, edx
|
|
|
|
|
jecxz @f
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov eax, [eax+(ecx-1)*4]
|
|
|
|
|
add eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov edx, [eax+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
add edx, [eax+_7z.StreamsInfo.startPackedStream]
|
|
|
|
|
@@:
|
|
|
|
|
mov [ebp+_7z.StreamsInfo.startPackedStream], edx
|
|
|
|
|
pop ebp
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jb .folderloop
|
|
|
|
|
.nofolders:
|
|
|
|
|
call _7z.UnswitchStream
|
|
|
|
|
mov ecx, kCodersUnPackSize
|
|
|
|
|
call _7z.WaitAttribute
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.6:
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jae .7
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
push ebp
|
|
|
|
|
mov ebp, [eax+ecx*4]
|
|
|
|
|
add ebp, eax
|
|
|
|
|
mov esi, [ebp+_7z.StreamsInfo.numOutStreams]
|
|
|
|
|
mov ebp, [ebp+_7z.StreamsInfo.unpackSizes]
|
|
|
|
|
add ebp, [_7z.StreamsInfo.folders]
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
mov dword [ebp], eax
|
|
|
|
|
mov dword [ebp+4], edx
|
|
|
|
|
add ebp, 8
|
|
|
|
|
dec esi
|
|
|
|
|
jnz @b
|
|
|
|
|
pop ebp
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp .6
|
|
|
|
|
.7:
|
|
|
|
|
; convert all relative addresses to pointers
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov edx, [_7z.StreamsInfo.folders]
|
|
|
|
|
.8:
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jae .9
|
|
|
|
|
lea eax, [edx+ecx*4]
|
|
|
|
|
add [eax], edx
|
|
|
|
|
mov eax, [eax]
|
|
|
|
|
add [eax+_7z.StreamsInfo.bindPairs], edx
|
|
|
|
|
add [eax+_7z.StreamsInfo.packedStreams], edx
|
|
|
|
|
add [eax+_7z.StreamsInfo.unpackSizes], edx
|
|
|
|
|
mov ebx, [eax+_7z.StreamsInfo.numCoders]
|
|
|
|
|
add eax, _7z.StreamsInfo.fsz
|
|
|
|
|
inc ecx
|
|
|
|
|
.11:
|
|
|
|
|
dec ebx
|
|
|
|
|
js .8
|
|
|
|
|
push eax
|
|
|
|
|
@@:
|
|
|
|
|
cmp dword [eax], 0
|
|
|
|
|
jz @f
|
|
|
|
|
add [eax], edx
|
|
|
|
|
mov eax, [eax]
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
pop eax
|
|
|
|
|
add eax, 4
|
|
|
|
|
jmp .11
|
|
|
|
|
.9:
|
|
|
|
|
; done
|
|
|
|
|
mov eax, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
lea edx, [edx+eax*4]
|
|
|
|
|
mov [_7z.StreamsInfo.unpackCRCsDefined], edx
|
|
|
|
|
add edx, eax
|
|
|
|
|
mov [_7z.StreamsInfo.unpackCRCs], edx
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .mainloop
|
|
|
|
|
cmp eax, kCRC
|
|
|
|
|
jz .unpackInfo.crc
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
jmp @b
|
|
|
|
|
.unpackInfo.crc:
|
|
|
|
|
mov esi, [_7z.StreamsInfo.unpackCRCs]
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.unpackCRCsDefined]
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
call _7z.ReadHashDigests
|
|
|
|
|
jmp @b
|
|
|
|
|
|
|
|
|
|
.SubStreamsInfo:
|
|
|
|
|
cmp [_7z.StreamsInfo.numFolders], 0
|
|
|
|
|
jz return.err
|
|
|
|
|
cmp [_7z.StreamsInfo.numSubStreams], 0
|
|
|
|
|
jnz return.err
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.folders]
|
|
|
|
|
.ssloop1:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
cmp eax, kNumUnPackStream
|
|
|
|
|
jz .NumUnPackStream
|
|
|
|
|
cmp eax, kCRC
|
|
|
|
|
jz .break1
|
|
|
|
|
cmp eax, kSize
|
|
|
|
|
jz .break1
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .break1
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
jmp .ssloop1
|
|
|
|
|
.NumUnPackStream:
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
mov edx, [ebx+ecx*4]
|
|
|
|
|
mov [edx+_7z.StreamsInfo.numUnPackStreams], eax
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jb @b
|
|
|
|
|
jmp .ssloop1
|
|
|
|
|
.break1:
|
|
|
|
|
; calculate number of substreams and number of defined digests
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
xor ebp, ebp
|
|
|
|
|
push 0
|
|
|
|
|
push eax
|
|
|
|
|
xor eax, eax
|
|
|
|
|
.ssloop2:
|
|
|
|
|
mov edx, [ebx+ecx*4]
|
|
|
|
|
mov edx, [edx+_7z.StreamsInfo.numUnPackStreams]
|
|
|
|
|
cmp edx, 1
|
|
|
|
|
jz @f
|
|
|
|
|
inc ebp
|
|
|
|
|
@@:
|
|
|
|
|
add eax, edx
|
|
|
|
|
jc return.err
|
|
|
|
|
cmp edx, 1
|
|
|
|
|
jnz @f
|
|
|
|
|
push eax
|
|
|
|
|
mov eax, [_7z.StreamsInfo.unpackCRCsDefined]
|
|
|
|
|
cmp byte [eax+ecx], 0
|
|
|
|
|
pop eax
|
|
|
|
|
jz @f
|
|
|
|
|
xor edx, edx
|
|
|
|
|
@@:
|
|
|
|
|
add [esp+4], edx
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jb .ssloop2
|
|
|
|
|
mov [_7z.StreamsInfo.numSubStreams], eax
|
|
|
|
|
imul ecx, eax, 4+8+1
|
|
|
|
|
jecxz .noss1
|
|
|
|
|
push eax
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
pop ecx
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [_7z.StreamsInfo.SubStreamsSizes], eax
|
|
|
|
|
lea eax, [eax+ecx*8]
|
|
|
|
|
mov [_7z.StreamsInfo.SubStreamsCRCsDefined], eax
|
|
|
|
|
add eax, ecx
|
|
|
|
|
mov [_7z.StreamsInfo.SubStreamsCRCs], eax
|
|
|
|
|
@@:
|
|
|
|
|
dec eax
|
|
|
|
|
mov byte [eax], 0
|
|
|
|
|
loop @b
|
|
|
|
|
.noss1:
|
|
|
|
|
mov ecx, [esp+4]
|
|
|
|
|
jecxz @f
|
|
|
|
|
imul ecx, 4+1
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [_7z.StreamsInfo.tmpSubStreamsCRCsDefined], eax
|
|
|
|
|
add eax, [esp+4]
|
|
|
|
|
mov [_7z.StreamsInfo.tmpSubStreamsCRCs], eax
|
|
|
|
|
@@:
|
|
|
|
|
test ebp, ebp
|
|
|
|
|
jz @f
|
|
|
|
|
cmp dword [esp], kSize
|
|
|
|
|
jnz return.err
|
|
|
|
|
@@:
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov ebp, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
.ssloop3:
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov ebx, [ebx+ecx*4]
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.numUnPackStreams]
|
|
|
|
|
dec eax
|
|
|
|
|
js .sscont3
|
|
|
|
|
push 0
|
|
|
|
|
push 0
|
|
|
|
|
@@:
|
|
|
|
|
dec eax
|
|
|
|
|
js @f
|
|
|
|
|
push eax
|
|
|
|
|
call _7z.ReadNumber
|
|
|
|
|
mov [ebp], eax
|
|
|
|
|
mov [ebp+4], edx
|
|
|
|
|
add ebp, 8
|
|
|
|
|
add [esp+4], eax
|
|
|
|
|
adc [esp+8], edx
|
|
|
|
|
jc return.err
|
|
|
|
|
pop eax
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
call _7z.GetUnPackSize
|
|
|
|
|
sub eax, [esp]
|
|
|
|
|
sbb edx, [esp+4]
|
|
|
|
|
jc return.err
|
|
|
|
|
mov [ebp], eax
|
|
|
|
|
mov [ebp+4], edx
|
|
|
|
|
add ebp, 8
|
|
|
|
|
add esp, 8
|
|
|
|
|
.sscont3:
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jb .ssloop3
|
|
|
|
|
pop eax
|
|
|
|
|
cmp eax, kSize
|
|
|
|
|
jnz @f
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
@@:
|
|
|
|
|
cmp eax, kCRC
|
|
|
|
|
jz .sscrc
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .ssend
|
|
|
|
|
call _7z.SkipData
|
|
|
|
|
.ssloop4:
|
|
|
|
|
call _7z.ReadNum
|
|
|
|
|
jmp @b
|
|
|
|
|
.sscrc:
|
|
|
|
|
pop ecx
|
|
|
|
|
push ecx
|
|
|
|
|
mov ebx, [_7z.StreamsInfo.tmpSubStreamsCRCsDefined]
|
|
|
|
|
mov esi, [_7z.StreamsInfo.tmpSubStreamsCRCs]
|
|
|
|
|
call _7z.ReadHashDigests
|
|
|
|
|
xor ecx, ecx ; index in out
|
|
|
|
|
xor edx, edx ; index in tmp
|
|
|
|
|
push -1
|
|
|
|
|
pop ebx ; index in folders
|
|
|
|
|
.ssloop5:
|
|
|
|
|
inc ebx
|
|
|
|
|
cmp ebx, [_7z.StreamsInfo.numFolders]
|
|
|
|
|
jae .ssloop4
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders]
|
|
|
|
|
mov ebp, [eax+ebx*4]
|
|
|
|
|
mov ebp, [ebp+_7z.StreamsInfo.numUnPackStreams]
|
|
|
|
|
cmp ebp, 1
|
|
|
|
|
jnz @f
|
|
|
|
|
mov eax, [_7z.StreamsInfo.unpackCRCsDefined]
|
|
|
|
|
cmp byte [eax+ebx], 0
|
|
|
|
|
jz @f
|
|
|
|
|
mov esi, [_7z.StreamsInfo.SubStreamsCRCsDefined]
|
|
|
|
|
mov byte [esi+ecx], 1
|
|
|
|
|
mov esi, [_7z.StreamsInfo.unpackCRCs]
|
|
|
|
|
mov eax, [esi+ebx*4]
|
|
|
|
|
mov esi, [_7z.StreamsInfo.SubStreamsCRCs]
|
|
|
|
|
mov [esi+ecx*4], eax
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp .ssloop5
|
|
|
|
|
@@:
|
|
|
|
|
dec ebp
|
|
|
|
|
js .ssloop5
|
|
|
|
|
mov esi, [_7z.StreamsInfo.tmpSubStreamsCRCsDefined]
|
|
|
|
|
mov al, [esi+edx]
|
|
|
|
|
mov esi, [_7z.StreamsInfo.SubStreamsCRCsDefined]
|
|
|
|
|
mov [esi+ecx], al
|
|
|
|
|
mov esi, [_7z.StreamsInfo.tmpSubStreamsCRCs]
|
|
|
|
|
mov eax, [esi+edx*4]
|
|
|
|
|
mov esi, [_7z.StreamsInfo.SubStreamsCRCs]
|
|
|
|
|
mov [esi+ecx*4], eax
|
|
|
|
|
inc edx
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp @b
|
|
|
|
|
.ssend:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.tmpSubStreamsCRCsDefined]
|
|
|
|
|
call [pgfree]
|
|
|
|
|
and [_7z.StreamsInfo.tmpSubStreamsCRCsDefined], 0
|
|
|
|
|
pop ecx
|
|
|
|
|
jmp .mainloop
|
|
|
|
|
|
|
|
|
|
.folders_alloc:
|
|
|
|
|
push ecx
|
|
|
|
|
add ecx, [_7z.StreamsInfo.folders.size]
|
|
|
|
|
sub ecx, [_7z.StreamsInfo.folders.alloc]
|
|
|
|
|
jbe @f
|
|
|
|
|
push edx
|
|
|
|
|
or ecx, 0xFFF
|
|
|
|
|
inc ecx
|
|
|
|
|
add ecx, [_7z.StreamsInfo.folders.alloc]
|
|
|
|
|
mov [_7z.StreamsInfo.folders.alloc], ecx
|
|
|
|
|
mov edx, [_7z.StreamsInfo.folders]
|
|
|
|
|
call [pgrealloc]
|
|
|
|
|
pop edx
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [_7z.StreamsInfo.folders], eax
|
|
|
|
|
@@:
|
|
|
|
|
pop ecx
|
|
|
|
|
mov eax, [_7z.StreamsInfo.folders.size]
|
|
|
|
|
add [_7z.StreamsInfo.folders.size], ecx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
.error:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.packSizes]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.folders]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.tmpSubStreamsCRCsDefined]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
jmp open_7z.header_error
|
|
|
|
|
.clear:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.packSizes]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.folders]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.SubStreamsSizes]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.StreamsInfo.tmpSubStreamsCRCsDefined]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
jmp open_7z.clear
|
|
|
|
|
|
|
|
|
|
uglobal
|
|
|
|
|
align 4
|
|
|
|
|
_7z.decode.mainbuf dd ?
|
|
|
|
|
_7z.decode.pStreams dd ?
|
|
|
|
|
_7z.decode.pStreams_def rd 8
|
|
|
|
|
_7z.decode.outBufferSize dd ?
|
|
|
|
|
_7z.decode.outBufferPtr dd ?
|
|
|
|
|
_7z.decode.outBufferRead dd ?
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
virtual at 0
|
|
|
|
|
streamInfo:
|
|
|
|
|
.fullSize dq ?
|
|
|
|
|
.fillBuf dd ? ; procedure which fills the buffer
|
|
|
|
|
.bufSize dd ?
|
|
|
|
|
.bufDataLen dd ?
|
|
|
|
|
.bufPtr dd ?
|
|
|
|
|
.size = $
|
|
|
|
|
end virtual
|
|
|
|
|
|
|
|
|
|
_7z.decode:
|
|
|
|
|
; in: ebx->folder, outBufferSize, outBufferPtr
|
|
|
|
|
; N.B. We assume that every coder has 1 output (unpacked) stream.
|
|
|
|
|
and [.mainbuf], 0
|
|
|
|
|
mov [.pStreams], .pStreams_def
|
|
|
|
|
mov [error_proc], .error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
call .init
|
|
|
|
|
and [.outBufferRead], 0
|
|
|
|
|
@@:
|
|
|
|
|
push edi
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.mainOutStream]
|
|
|
|
|
mov esi, [.pStreams]
|
|
|
|
|
mov eax, [esi+eax*4]
|
|
|
|
|
call fillBuf
|
|
|
|
|
mov ecx, [eax+streamInfo.bufSize]
|
|
|
|
|
mov esi, [eax+streamInfo.bufPtr]
|
|
|
|
|
mov edi, [.outBufferPtr]
|
|
|
|
|
add edi, [.outBufferRead]
|
|
|
|
|
add [.outBufferRead], ecx
|
|
|
|
|
mov edx, ecx
|
|
|
|
|
shr ecx, 2
|
|
|
|
|
rep movsd
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
and ecx, 3
|
|
|
|
|
rep movsb
|
|
|
|
|
pop edi
|
|
|
|
|
mov eax, [.outBufferRead]
|
|
|
|
|
cmp eax, [.outBufferSize]
|
|
|
|
|
jb @b
|
|
|
|
|
mov ecx, [.pStreams]
|
|
|
|
|
cmp ecx, .pStreams_def
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [.mainbuf]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov [error_proc], _7z.ReadAndDecodePackedStreams.error
|
|
|
|
|
mov [clear_proc], _7z.ReadAndDecodePackedStreams.clear
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
.error:
|
|
|
|
|
mov ecx, [.pStreams]
|
|
|
|
|
cmp ecx, .pStreams_def
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [.mainbuf]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
jmp _7z.ReadAndDecodePackedStreams.error
|
|
|
|
|
.clear:
|
|
|
|
|
mov ecx, [.pStreams]
|
|
|
|
|
cmp ecx, .pStreams_def
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [.mainbuf]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
jmp _7z.ReadAndDecodePackedStreams.clear
|
|
|
|
|
|
|
|
|
|
.init:
|
|
|
|
|
; We use stack to keep some information on streams,
|
|
|
|
|
; to avoid stack overflow we limit possible number of coders.
|
|
|
|
|
; Anyway, in real life maximum number of coders is 5
|
|
|
|
|
; (password protection filter + BCJ2 filter + 3 LZMA coders),
|
|
|
|
|
; from command line user can define more coders, but
|
|
|
|
|
; archive with, say, 32 coders is most likely bogus.
|
|
|
|
|
cmp [ebx+_7z.StreamsInfo.numCoders], 128
|
|
|
|
|
ja return.err
|
|
|
|
|
; allocate space for streams info array
|
|
|
|
|
mov eax, .pStreams_def
|
|
|
|
|
mov ecx, [ebx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
add ecx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
cmp ecx, 8
|
|
|
|
|
jbe @f
|
|
|
|
|
shl ecx, 2
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
@@:
|
|
|
|
|
mov [.pStreams], eax
|
|
|
|
|
; calculate size of buffers required for decoders
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
push ecx
|
|
|
|
|
mov ebp, [ebx+_7z.StreamsInfo.unpackSizes]
|
|
|
|
|
.calcbufsz:
|
|
|
|
|
; LZMA decoder: method ID = [size=03] 03 01 01, NumInStreams = NumOutStreams = 1
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+ecx*4]
|
|
|
|
|
call _7z.GetCoder
|
|
|
|
|
jnc .known_id
|
|
|
|
|
.unknown_method_id:
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
lea ecx, [eax+5]
|
|
|
|
|
mov ebx, aUnknownMethod.z
|
|
|
|
|
@@:
|
|
|
|
|
dec esi
|
|
|
|
|
js @f
|
|
|
|
|
mov byte [ebx], ' '
|
|
|
|
|
inc ebx
|
|
|
|
|
mov al, [ecx]
|
|
|
|
|
push eax
|
|
|
|
|
shr al, 4
|
|
|
|
|
cmp al, 10
|
|
|
|
|
sbb al, 69h
|
|
|
|
|
das
|
|
|
|
|
mov [ebx], al
|
|
|
|
|
inc ebx
|
|
|
|
|
pop eax
|
|
|
|
|
and al, 0xF
|
|
|
|
|
cmp al, 10
|
|
|
|
|
sbb al, 69h
|
|
|
|
|
das
|
|
|
|
|
mov [ebx], al
|
|
|
|
|
inc ebx
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
mov byte [ebx], 0
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aUnknownMethod_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
jmp return.clear
|
|
|
|
|
iglobal
|
|
|
|
|
if lang eq ru
|
|
|
|
|
aUnknownMethod db '<27><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD> <20><>⮤:'
|
|
|
|
|
else
|
|
|
|
|
aUnknownMethod db 'Unknown method:'
|
|
|
|
|
end if
|
|
|
|
|
.z:
|
|
|
|
|
times 16*3+1 db 0
|
|
|
|
|
aUnknownMethod_ptr dd aUnknownMethod
|
|
|
|
|
endg
|
|
|
|
|
.known_id:
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
lea esi, [esi+eax+17]
|
|
|
|
|
call [_7z.GetBufSizeTable+edx*4]
|
|
|
|
|
add eax, 3
|
|
|
|
|
and al, not 3
|
|
|
|
|
add [esp], eax
|
|
|
|
|
jc .nomem
|
|
|
|
|
cmp dword [ebp+4], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [ebp], edx
|
|
|
|
|
jae @f
|
|
|
|
|
mov edx, [ebp]
|
|
|
|
|
@@:
|
|
|
|
|
add edx, 0xF
|
|
|
|
|
and edx, not 0xF
|
|
|
|
|
add [esp], edx
|
|
|
|
|
jc .nomem
|
|
|
|
|
add ebp, 8
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
jb .calcbufsz
|
|
|
|
|
; add 4 pages for each of not binded input streams
|
|
|
|
|
mov ecx, [ebx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
shl ecx, 14
|
|
|
|
|
add [esp], ecx
|
|
|
|
|
;; calculate free RAM
|
|
|
|
|
; call [getfreemem]
|
|
|
|
|
; sub eax, 64 ; keep at least 64 Kb of free RAM
|
|
|
|
|
; jbe .nomem
|
|
|
|
|
; pop ecx
|
|
|
|
|
; push ecx
|
|
|
|
|
; add ecx, 0x3FF
|
|
|
|
|
; shr ecx, 10
|
|
|
|
|
; cmp eax, ecx
|
|
|
|
|
; jae .memok
|
|
|
|
|
jmp .memok
|
|
|
|
|
.nomem:
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aNoFreeRam_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
jmp return.clear
|
|
|
|
|
.memok:
|
|
|
|
|
; allocate streamInfos
|
|
|
|
|
pop ecx
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov [.mainbuf], eax
|
|
|
|
|
; initialize streamInfos for decoders
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov ebp, [ebx+_7z.StreamsInfo.unpackSizes]
|
|
|
|
|
mov edx, [.pStreams]
|
|
|
|
|
.init1:
|
|
|
|
|
mov [edx], eax
|
|
|
|
|
add edx, 4
|
|
|
|
|
push edx
|
|
|
|
|
push dword [ebp]
|
|
|
|
|
pop dword [eax]
|
|
|
|
|
push dword [ebp+4]
|
|
|
|
|
pop dword [eax+4]
|
|
|
|
|
and dword [eax+streamInfo.size], 0
|
|
|
|
|
push eax
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+ecx*4]
|
|
|
|
|
call _7z.GetCoder
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
lea esi, [esi+eax+17]
|
|
|
|
|
call [_7z.GetBufSizeTable+edx*4]
|
|
|
|
|
pop esi
|
|
|
|
|
push esi
|
|
|
|
|
add eax, 3
|
|
|
|
|
and al, not 3
|
|
|
|
|
add [esp], eax
|
|
|
|
|
pop [esi+streamInfo.bufPtr]
|
|
|
|
|
push [esi+streamInfo.bufPtr]
|
|
|
|
|
cmp dword [ebp+4], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [ebp], edx
|
|
|
|
|
jae @f
|
|
|
|
|
mov edx, [ebp]
|
|
|
|
|
@@:
|
|
|
|
|
add edx, 0xF
|
|
|
|
|
and edx, not 0xF
|
|
|
|
|
mov [esi+streamInfo.bufSize], edx
|
|
|
|
|
and [esi+streamInfo.bufDataLen], 0
|
|
|
|
|
pop eax
|
|
|
|
|
add eax, edx
|
|
|
|
|
pop edx
|
|
|
|
|
add ebp, 8
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
jb .init1
|
|
|
|
|
; initialize streamInfos for input streams
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
@@:
|
|
|
|
|
mov [edx], eax
|
|
|
|
|
add edx, 4
|
|
|
|
|
mov esi, [_7z.CurInStream]
|
|
|
|
|
inc [_7z.CurInStream]
|
|
|
|
|
shl esi, 3
|
|
|
|
|
add esi, [_7z.StreamsInfo.packSizes]
|
|
|
|
|
push dword [esi]
|
|
|
|
|
pop dword [eax]
|
|
|
|
|
push dword [esi+4]
|
|
|
|
|
pop dword [eax+4]
|
|
|
|
|
mov [eax+streamInfo.fillBuf], fillBufFromInStream
|
|
|
|
|
lea esi, [eax+streamInfo.size+8]
|
|
|
|
|
mov [eax+streamInfo.bufPtr], esi
|
|
|
|
|
mov [eax+streamInfo.bufSize], 0x4000 - streamInfo.size - 8
|
|
|
|
|
and [eax+streamInfo.bufDataLen], 0
|
|
|
|
|
mov esi, dword [_7z.StreamsInfo.dataOffset]
|
|
|
|
|
mov dword [eax+streamInfo.size], esi
|
|
|
|
|
mov esi, dword [_7z.StreamsInfo.dataOffset+4]
|
|
|
|
|
mov dword [eax+streamInfo.size+4], esi
|
|
|
|
|
mov esi, [eax]
|
|
|
|
|
add dword [_7z.StreamsInfo.dataOffset], esi
|
|
|
|
|
mov esi, [eax+4]
|
|
|
|
|
adc dword [_7z.StreamsInfo.dataOffset+4], esi
|
|
|
|
|
add eax, 0x4000
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
jb @b
|
|
|
|
|
; initialize links between streams
|
|
|
|
|
push -1
|
|
|
|
|
mov edx, [ebx+_7z.StreamsInfo.mainOutStream]
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.init_links:
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+edx*4]
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
cmp ecx, [eax+esi+5]
|
|
|
|
|
jb @f
|
|
|
|
|
pop ecx
|
|
|
|
|
cmp ecx, -1
|
|
|
|
|
jz .inited_links
|
|
|
|
|
pop edx
|
|
|
|
|
jmp .init_links
|
|
|
|
|
@@:
|
|
|
|
|
push edx
|
|
|
|
|
push ecx
|
|
|
|
|
@@:
|
|
|
|
|
dec edx
|
|
|
|
|
js @f
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+edx*4]
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
add ecx, [eax+esi+5]
|
|
|
|
|
jmp @b
|
|
|
|
|
@@:
|
|
|
|
|
mov esi, [ebx+_7z.StreamsInfo.bindPairs]
|
|
|
|
|
mov edx, [ebx+_7z.StreamsInfo.numBindPairs]
|
|
|
|
|
@@:
|
|
|
|
|
add esi, 8
|
|
|
|
|
dec edx
|
|
|
|
|
js .link_to_in
|
|
|
|
|
cmp ecx, [esi-8]
|
|
|
|
|
jnz @b
|
|
|
|
|
pop ecx
|
|
|
|
|
pop edx
|
|
|
|
|
mov eax, [.pStreams]
|
|
|
|
|
mov eax, [eax+edx*4]
|
|
|
|
|
lea eax, [eax+streamInfo.size+ecx*4]
|
|
|
|
|
push edx
|
|
|
|
|
inc ecx
|
|
|
|
|
push ecx
|
|
|
|
|
mov edx, [esi-4]
|
|
|
|
|
mov ecx, [.pStreams]
|
|
|
|
|
mov ecx, [ecx+edx*4]
|
|
|
|
|
mov [eax], ecx
|
|
|
|
|
cmp dword [ecx+streamInfo.size], 0
|
|
|
|
|
jnz return.err
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
jmp .init_links
|
|
|
|
|
.link_to_in:
|
|
|
|
|
mov esi, [ebx+_7z.StreamsInfo.packedStreams]
|
|
|
|
|
mov edx, [ebx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
@@:
|
|
|
|
|
dec edx
|
|
|
|
|
js return.err
|
|
|
|
|
cmp ecx, [esi+edx*4]
|
|
|
|
|
jnz @b
|
|
|
|
|
add edx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
mov esi, [.pStreams]
|
|
|
|
|
mov eax, [esi+edx*4]
|
|
|
|
|
pop ecx
|
|
|
|
|
pop edx
|
|
|
|
|
mov esi, [esi+edx*4]
|
|
|
|
|
mov [esi+streamInfo.size+ecx*4], eax
|
|
|
|
|
inc ecx
|
|
|
|
|
jmp .init_links
|
|
|
|
|
.inited_links:
|
|
|
|
|
; initialize all decoders
|
|
|
|
|
; bool zzz_init_decoder(stream_info* ebp, esi->params, [esi-4]=params_size);
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
.init_decoders:
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+ecx*4]
|
|
|
|
|
call _7z.GetCoder
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
mov ebp, [.pStreams]
|
|
|
|
|
mov ebp, [ebp+ecx*4]
|
|
|
|
|
cmp dword [esi+eax], 0
|
|
|
|
|
jz @f
|
|
|
|
|
cmp dword [ebp+streamInfo.size], 0
|
|
|
|
|
jz return.err
|
|
|
|
|
@@:
|
|
|
|
|
lea esi, [esi+eax+17]
|
|
|
|
|
push ebx ecx edi
|
|
|
|
|
xor ebx, ebx
|
|
|
|
|
call [_7z.InitTable+edx*4]
|
|
|
|
|
pop edi ecx ebx
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
jb .init_decoders
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
fillBuf:
|
|
|
|
|
and [eax+streamInfo.bufDataLen], 0
|
|
|
|
|
fillBufNozero:
|
|
|
|
|
pushad
|
|
|
|
|
mov edx, [eax+streamInfo.bufSize]
|
|
|
|
|
sub edx, [eax+streamInfo.bufDataLen]
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize+4], 0
|
|
|
|
|
jnz .full
|
|
|
|
|
mov ecx, dword [eax+streamInfo.fullSize]
|
|
|
|
|
cmp ecx, edx
|
|
|
|
|
jbe @f
|
|
|
|
|
.full:
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
@@:
|
|
|
|
|
sub dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
sbb dword [eax+streamInfo.fullSize+4], 0
|
|
|
|
|
mov edi, [eax+streamInfo.bufPtr]
|
|
|
|
|
add edi, [eax+streamInfo.bufDataLen]
|
|
|
|
|
add [eax+streamInfo.bufDataLen], ecx
|
|
|
|
|
jmp [eax+streamInfo.fillBuf]
|
|
|
|
|
|
|
|
|
|
fillBufFromInStream:
|
|
|
|
|
push eax
|
|
|
|
|
push dword [eax+streamInfo.size+4]
|
|
|
|
|
push dword [eax+streamInfo.size]
|
|
|
|
|
push 0
|
|
|
|
|
push [inStream]
|
|
|
|
|
call [seek]
|
|
|
|
|
push ecx
|
|
|
|
|
push edi
|
|
|
|
|
push [inStream]
|
|
|
|
|
call [read]
|
|
|
|
|
cmp eax, ecx
|
|
|
|
|
pop eax
|
|
|
|
|
jnz .error
|
|
|
|
|
add dword [eax+streamInfo.size], ecx
|
|
|
|
|
adc dword [eax+streamInfo.size+4], 0
|
|
|
|
|
popad
|
|
|
|
|
ret
|
|
|
|
|
.error:
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aReadError_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
jmp return.clear
|
|
|
|
|
|
|
|
|
|
_7z.GetCoder:
|
|
|
|
|
; in: eax->coder
|
|
|
|
|
; out: edx = coder type
|
|
|
|
|
xor edx, edx
|
|
|
|
|
; Copy decoder: method ID = [size=01] 00, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp word [eax+4], 0x0001
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+6], 1
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; LZMA decoder: method ID = [size=03] 03 01 01, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp dword [eax+4], 0x01010303
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+8], 1
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; PPMD decoder: method ID = [size=03] 03 04 01, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp dword [eax+4], 0x01040303
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+8], 1
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; BCJ filter: method ID = [size=04] 03 03 01 03, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp byte [eax+4], 4
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+5], 0x03010303
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+9], 1
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; BCJ2 filter: method ID = [size=04] 03 03 01 1B, NumInStreams = 4, NumOutStreams = 1
|
|
|
|
|
cmp byte [eax+4], 4
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+5], 0x1B010303
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+9], 4
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; 7z-AES cryptor: method ID = [size=04] 06 F1 07 01, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp byte [eax+4], 4
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+5], 0x0107F106
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+9], 1
|
|
|
|
|
jz .ret
|
2007-09-20 18:20:58 +02:00
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; Deflate decoder: method ID = [size=03] 04 01 08, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp dword [eax+4], 0x08010403
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+8], 1
|
|
|
|
|
jz .ret
|
|
|
|
|
@@:
|
|
|
|
|
inc edx
|
|
|
|
|
; Deflate64 decoder: method ID = [size=03] 04 01 09, NumInStreams = NumOutStreams = 1
|
|
|
|
|
cmp dword [eax+4], 0x09010403
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+8], 1
|
|
|
|
|
jz .ret
|
2007-07-26 14:45:49 +02:00
|
|
|
|
@@:
|
|
|
|
|
stc
|
|
|
|
|
.ret:
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
iglobal
|
|
|
|
|
align 4
|
|
|
|
|
label _7z.GetBufSizeTable dword
|
|
|
|
|
dd copy_get_buf_size
|
|
|
|
|
dd lzma_get_buf_size
|
|
|
|
|
dd ppmd_get_buf_size
|
|
|
|
|
dd bcj_get_buf_size
|
|
|
|
|
dd bcj2_get_buf_size
|
|
|
|
|
dd aes7z_get_buf_size
|
2007-09-20 18:20:58 +02:00
|
|
|
|
dd deflate_get_buf_size
|
|
|
|
|
dd deflate_get_buf_size
|
2007-07-26 14:45:49 +02:00
|
|
|
|
label _7z.InitTable dword
|
|
|
|
|
dd copy_init_decoder
|
|
|
|
|
dd lzma_init_decoder
|
|
|
|
|
dd ppmd_init_decoder
|
|
|
|
|
dd bcj_init_decoder
|
|
|
|
|
dd bcj2_init_decoder
|
|
|
|
|
dd aes7z_init_decoder
|
2007-09-20 18:20:58 +02:00
|
|
|
|
dd deflate_init_decoder
|
|
|
|
|
dd deflate64_init_decoder
|
2007-07-26 14:45:49 +02:00
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
copy_get_buf_size:
|
|
|
|
|
mov eax, streamInfo.size+8
|
|
|
|
|
mov edx, 0x10000
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
copy_init_decoder:
|
|
|
|
|
mov [ebp+streamInfo.fillBuf], copy_fillBuf
|
|
|
|
|
and dword [ebp+streamInfo.size+4], 0
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
copy_fillBuf:
|
|
|
|
|
push eax
|
|
|
|
|
mov esi, [eax+streamInfo.size+4]
|
|
|
|
|
mov eax, [eax+streamInfo.size]
|
|
|
|
|
.redo:
|
|
|
|
|
push ecx
|
|
|
|
|
mov edx, [eax+streamInfo.bufDataLen]
|
|
|
|
|
sub edx, esi
|
|
|
|
|
cmp ecx, edx
|
|
|
|
|
jb @f
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
@@:
|
|
|
|
|
sub [esp], ecx
|
|
|
|
|
add esi, [eax+streamInfo.bufPtr]
|
|
|
|
|
mov edx, ecx
|
|
|
|
|
shr ecx, 2
|
|
|
|
|
rep movsd
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
and ecx, 3
|
|
|
|
|
rep movsb
|
|
|
|
|
pop ecx
|
|
|
|
|
jecxz .done
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize+4], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
jb return.err
|
|
|
|
|
@@:
|
|
|
|
|
call fillBuf
|
|
|
|
|
xor esi, esi
|
|
|
|
|
jmp .redo
|
|
|
|
|
.done:
|
|
|
|
|
sub esi, [eax+streamInfo.bufPtr]
|
|
|
|
|
pop eax
|
|
|
|
|
mov [eax+streamInfo.size+4], esi
|
|
|
|
|
popad
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
; ebp=hPlugin, eax->item, edi->info
|
|
|
|
|
getattr_7z:
|
|
|
|
|
cmp [eax+file_in_7z.bPseudoFolder], 0
|
|
|
|
|
jnz .pseudo
|
|
|
|
|
lea esi, [eax+file_in_7z.attr]
|
|
|
|
|
movsd
|
|
|
|
|
xor eax, eax
|
|
|
|
|
stosd
|
|
|
|
|
add esi, -(file_in_7z.attr+4) + file_in_7z.CreationTime
|
|
|
|
|
mov ecx, 8
|
|
|
|
|
rep movsd
|
|
|
|
|
ret
|
|
|
|
|
.pseudo:
|
|
|
|
|
push 0x10 ; attributes: folder
|
|
|
|
|
pop eax
|
|
|
|
|
stosd
|
|
|
|
|
xor eax, eax
|
|
|
|
|
stosd
|
|
|
|
|
lea esi, [ebp+handle_7z.host_datetime]
|
|
|
|
|
push 6
|
|
|
|
|
pop ecx
|
|
|
|
|
rep movsd
|
|
|
|
|
stosd
|
|
|
|
|
stosd
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
virtual at 0
|
|
|
|
|
file_handle_7z:
|
|
|
|
|
.type dd ?
|
|
|
|
|
.context dd ?
|
|
|
|
|
.pos dq ?
|
|
|
|
|
.base dd ? ; handle of archive
|
|
|
|
|
.item dd ? ; pointer to file_in_7z
|
|
|
|
|
.mainStream dd ? ; (pointer in context)
|
|
|
|
|
.bError db ?
|
|
|
|
|
rb 3
|
|
|
|
|
.size = $
|
|
|
|
|
end virtual
|
|
|
|
|
|
|
|
|
|
iglobal
|
|
|
|
|
align 4
|
|
|
|
|
handle_table_7z dd handle_table_7z,handle_table_7z
|
|
|
|
|
endg
|
|
|
|
|
|
|
|
|
|
; ebp=hPlugin, eax->item, edi=mode
|
|
|
|
|
open_file_7z:
|
|
|
|
|
cmp [eax+file_in_7z.bHasStream], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
mov eax, empty_7z_handle
|
|
|
|
|
ret
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [ebp+handle_7z.password_len]
|
|
|
|
|
inc ecx
|
|
|
|
|
setnz [bPasswordDefined]
|
|
|
|
|
jz @f
|
|
|
|
|
dec ecx
|
|
|
|
|
lea esi, [ebp+handle_7z.password]
|
|
|
|
|
push edi
|
|
|
|
|
mov edi, password_unicode
|
|
|
|
|
shr ecx, 1
|
|
|
|
|
rep movsd
|
|
|
|
|
adc ecx, ecx
|
|
|
|
|
rep movsw
|
|
|
|
|
pop edi
|
|
|
|
|
@@:
|
|
|
|
|
mov [hOut], ecx
|
|
|
|
|
mov [_7z.decode.mainbuf], ecx
|
|
|
|
|
mov ecx, [ebp+handle_7z.host]
|
|
|
|
|
mov [inStream], ecx
|
|
|
|
|
mov [_7z.decode.pStreams], _7z.decode.pStreams_def
|
|
|
|
|
push eax
|
|
|
|
|
mov [_esp], esp
|
|
|
|
|
mov [_ebp], ebp
|
|
|
|
|
mov [error_proc], .error
|
|
|
|
|
mov [clear_proc], .clear
|
|
|
|
|
mov ebx, [ebp+handle_7z.folders]
|
|
|
|
|
mov ecx, [eax+file_in_7z.folder]
|
|
|
|
|
cmp [ebp+handle_7z.last_folder], ecx
|
|
|
|
|
jnz .nolast
|
|
|
|
|
mov edx, dword [eax+file_in_7z.folderStart]
|
|
|
|
|
sub edx, dword [ebp+handle_7z.last_pos]
|
|
|
|
|
mov esi, dword [eax+file_in_7z.folderStart+4]
|
|
|
|
|
sbb esi, dword [ebp+handle_7z.last_pos+4]
|
|
|
|
|
jb .nolast
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
xchg ecx, [ebp+handle_7z.last_context]
|
|
|
|
|
mov [_7z.decode.mainbuf], ecx
|
|
|
|
|
mov eax, [ebp+handle_7z.last_main_stream]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], edx
|
|
|
|
|
mov dword [eax+streamInfo.fullSize+4], esi
|
|
|
|
|
or [ebp+handle_7z.last_folder], -1
|
|
|
|
|
pop esi
|
|
|
|
|
push esi
|
|
|
|
|
jmp .commonl
|
|
|
|
|
.nolast:
|
|
|
|
|
mov ebx, [ebx+ecx*4]
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.startPackedStream]
|
|
|
|
|
mov [_7z.CurInStream], eax
|
|
|
|
|
mov eax, dword [ebx+_7z.StreamsInfo.packOffset]
|
|
|
|
|
mov dword [_7z.StreamsInfo.dataOffset], eax
|
|
|
|
|
mov eax, dword [ebx+_7z.StreamsInfo.packOffset+4]
|
|
|
|
|
mov dword [_7z.StreamsInfo.dataOffset+4], eax
|
|
|
|
|
mov eax, [ebp+handle_7z.packSizes]
|
|
|
|
|
mov [_7z.StreamsInfo.packSizes], eax
|
|
|
|
|
push ebp
|
|
|
|
|
call _7z.decode.init
|
|
|
|
|
pop ebp
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.mainOutStream]
|
|
|
|
|
mov esi, [_7z.decode.pStreams]
|
|
|
|
|
mov eax, [esi+eax*4]
|
|
|
|
|
pop esi
|
|
|
|
|
push esi
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.folderStart]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.folderStart+4]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize+4], ecx
|
|
|
|
|
.commonl:
|
|
|
|
|
call skip_7z
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.UnPackSize]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
mov edx, dword [esi+file_in_7z.UnPackSize+4]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize+4], edx
|
|
|
|
|
test edx, edx
|
|
|
|
|
jnz .nomemstream
|
|
|
|
|
if defined LIMIT_FOR_MEM_STREAM
|
|
|
|
|
cmp ecx, LIMIT_FOR_MEM_STREAM
|
|
|
|
|
ja .nomemstream
|
|
|
|
|
end if
|
|
|
|
|
push eax ecx
|
|
|
|
|
add ecx, 0x3FF
|
|
|
|
|
shr ecx, 10 ; get size in Kb
|
|
|
|
|
call [getfreemem]
|
|
|
|
|
shr eax, 2
|
|
|
|
|
cmp ecx, eax
|
|
|
|
|
pop ecx eax
|
|
|
|
|
ja .nomemstream
|
|
|
|
|
; create memory stream and unpack to memory
|
|
|
|
|
push eax ecx
|
|
|
|
|
add ecx, mem_stream.buf
|
|
|
|
|
call [pgalloc]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz return.clear
|
|
|
|
|
mov edi, eax
|
|
|
|
|
pop ecx
|
|
|
|
|
push edi
|
|
|
|
|
mov [hOut], eax
|
|
|
|
|
xor eax, eax ; type_mem_stream
|
|
|
|
|
stosd ; mem_stream.type
|
|
|
|
|
mov eax, ecx
|
|
|
|
|
stosd ; mem_stream.size
|
|
|
|
|
xor eax, eax
|
|
|
|
|
stosd ; mem_stream.pos
|
|
|
|
|
mov eax, [esp+4]
|
|
|
|
|
push esi
|
|
|
|
|
push ecx edi
|
|
|
|
|
call read_7z_to_buf
|
|
|
|
|
pop esi ecx
|
|
|
|
|
mov ebx, [esp+12]
|
|
|
|
|
cmp [ebx+file_in_7z.bCRCDefined], 0
|
|
|
|
|
jz @f
|
|
|
|
|
call crc
|
|
|
|
|
cmp eax, [ebx+file_in_7z.FileCRC]
|
|
|
|
|
jnz return.err
|
|
|
|
|
@@:
|
|
|
|
|
pop esi
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
xchg ecx, [_7z.decode.mainbuf]
|
|
|
|
|
xchg ecx, [ebp+handle_7z.last_context]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
and [hOut], 0
|
|
|
|
|
mov eax, [esi+file_in_7z.folder]
|
|
|
|
|
mov [ebp+handle_7z.last_folder], eax
|
|
|
|
|
mov eax, [esp+4]
|
|
|
|
|
mov [ebp+handle_7z.last_main_stream], eax
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.UnPackSize]
|
|
|
|
|
add ecx, dword [esi+file_in_7z.folderStart]
|
|
|
|
|
mov dword [ebp+handle_7z.last_pos], ecx
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.UnPackSize+4]
|
|
|
|
|
adc ecx, dword [esi+file_in_7z.folderStart+4]
|
|
|
|
|
mov dword [ebp+handle_7z.last_pos+4], ecx
|
|
|
|
|
call .done
|
|
|
|
|
pop eax edi ecx
|
|
|
|
|
ret
|
|
|
|
|
.nomemstream:
|
|
|
|
|
mov edi, eax
|
|
|
|
|
push esi
|
|
|
|
|
mov esi, handle_table_7z
|
|
|
|
|
push file_handle_7z.size
|
|
|
|
|
pop ecx
|
|
|
|
|
call alloc_handle
|
|
|
|
|
pop esi
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .clear
|
|
|
|
|
mov [eax+file_handle_7z.type], type_7z
|
|
|
|
|
xor edx, edx
|
|
|
|
|
mov dword [eax+file_handle_7z.pos], edx
|
|
|
|
|
mov dword [eax+file_handle_7z.pos+4], edx
|
|
|
|
|
mov [eax+file_handle_7z.bError], dl
|
|
|
|
|
xchg edx, [_7z.decode.mainbuf]
|
|
|
|
|
mov [eax+file_handle_7z.context], edx
|
|
|
|
|
mov [eax+file_handle_7z.mainStream], edi
|
|
|
|
|
mov [eax+file_handle_7z.base], ebp
|
|
|
|
|
mov [eax+file_handle_7z.item], esi
|
|
|
|
|
push eax
|
|
|
|
|
call .done
|
|
|
|
|
pop eax ecx
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
.done:
|
|
|
|
|
cmp [bPasswordDefined], 0
|
|
|
|
|
jz @f
|
|
|
|
|
mov ecx, [password_size]
|
|
|
|
|
mov [ebp+handle_7z.password_len], ecx
|
|
|
|
|
mov esi, password_unicode
|
|
|
|
|
lea edi, [ebp+handle_7z.password]
|
|
|
|
|
shr ecx, 1
|
|
|
|
|
rep movsd
|
|
|
|
|
adc ecx, ecx
|
|
|
|
|
rep movsw
|
|
|
|
|
@@:
|
|
|
|
|
jmp .clear
|
|
|
|
|
|
|
|
|
|
.error:
|
|
|
|
|
cmp [bPasswordDefined], 0
|
|
|
|
|
jz .realerror
|
|
|
|
|
push CancelPassBtn
|
|
|
|
|
push 2
|
|
|
|
|
push aArchiveDataErrorPass_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
cmp al, 1
|
|
|
|
|
jnz .clear
|
|
|
|
|
; user wants to re-enter password
|
|
|
|
|
call .clear
|
|
|
|
|
pop eax
|
|
|
|
|
jmp open_file_7z
|
|
|
|
|
.realerror:
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aArchiveDataError_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
.clear:
|
|
|
|
|
mov ecx, [_7z.decode.pStreams]
|
|
|
|
|
cmp ecx, _7z.decode.pStreams_def
|
|
|
|
|
jz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [_7z.decode.mainbuf]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov ecx, [hOut]
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
cmp esp, [_esp]
|
|
|
|
|
jnz @f
|
|
|
|
|
pop eax
|
|
|
|
|
@@:
|
|
|
|
|
xor eax, eax
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
read_7z_to_buf:
|
|
|
|
|
mov esi, [eax+streamInfo.bufDataLen]
|
|
|
|
|
cmp esi, [eax+streamInfo.bufSize]
|
|
|
|
|
jnz @f
|
|
|
|
|
xor esi, esi
|
|
|
|
|
mov [eax+streamInfo.bufDataLen], esi
|
|
|
|
|
@@:
|
|
|
|
|
call fillBufNozero
|
|
|
|
|
mov ecx, [eax+streamInfo.bufDataLen]
|
|
|
|
|
sub ecx, esi
|
|
|
|
|
add esi, [eax+streamInfo.bufPtr]
|
|
|
|
|
mov edx, ecx
|
|
|
|
|
shr ecx, 2
|
|
|
|
|
rep movsd
|
|
|
|
|
mov ecx, edx
|
|
|
|
|
and ecx, 3
|
|
|
|
|
rep movsb
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize], 0
|
|
|
|
|
jnz read_7z_to_buf
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
skip_7z:
|
|
|
|
|
push edx
|
|
|
|
|
mov edx, [eax+streamInfo.bufDataLen]
|
|
|
|
|
cmp edx, [eax+streamInfo.bufSize]
|
|
|
|
|
jnz @f
|
|
|
|
|
and [eax+streamInfo.bufDataLen], 0
|
|
|
|
|
@@:
|
|
|
|
|
pop edx
|
|
|
|
|
call fillBufNozero
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize], 0
|
|
|
|
|
jnz skip_7z
|
|
|
|
|
cmp dword [eax+streamInfo.fullSize+4], 0
|
|
|
|
|
jnz skip_7z
|
|
|
|
|
ret
|
|
|
|
|
|
|
|
|
|
; unsigned __stdcall read(HANDLE hFile, void* buf, unsigned size);
|
|
|
|
|
read_7z:
|
|
|
|
|
mov eax, [ebx+file_handle_7z.mainStream]
|
|
|
|
|
test eax, eax
|
|
|
|
|
jz .ret ; empty stream - return 0 bytes read
|
|
|
|
|
cmp [ebx+file_handle_7z.bError], 0
|
|
|
|
|
jnz .reterr
|
|
|
|
|
mov ecx, [ebx+file_handle_7z.base]
|
|
|
|
|
mov ecx, [ecx+handle_7z.host]
|
|
|
|
|
mov [inStream], ecx
|
|
|
|
|
mov edi, [esp+8]
|
|
|
|
|
mov ecx, [esp+12]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
and dword [eax+streamInfo.fullSize+4], 0
|
|
|
|
|
jecxz .nodata
|
|
|
|
|
mov [_esp], esp
|
|
|
|
|
mov [_ebp], ebp
|
|
|
|
|
mov [error_proc], .error
|
|
|
|
|
mov [clear_proc], .clear ; should not be called
|
|
|
|
|
mov esi, [ebx+file_handle_7z.item]
|
|
|
|
|
mov edx, dword [esi+file_in_7z.UnPackSize]
|
|
|
|
|
mov esi, dword [esi+file_in_7z.UnPackSize+4]
|
|
|
|
|
sub edx, dword [ebx+file_handle_7z.pos]
|
|
|
|
|
sbb esi, dword [ebx+file_handle_7z.pos+4]
|
|
|
|
|
jnz .do
|
|
|
|
|
cmp edx, ecx
|
|
|
|
|
jae .do
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], edx
|
|
|
|
|
.do:
|
|
|
|
|
call read_7z_to_buf
|
|
|
|
|
.nodata:
|
|
|
|
|
sub edi, [esp+8]
|
|
|
|
|
mov eax, edi
|
|
|
|
|
add dword [ebx+file_handle_7z.pos], eax
|
|
|
|
|
adc dword [ebx+file_handle_7z.pos+4], 0
|
|
|
|
|
.ret:
|
|
|
|
|
ret 12
|
|
|
|
|
|
|
|
|
|
.error:
|
|
|
|
|
.clear:
|
|
|
|
|
mov ebx, [esp+4]
|
|
|
|
|
mov [ebx+file_handle_7z.bError], 1
|
|
|
|
|
push ContinueBtn
|
|
|
|
|
push 1
|
|
|
|
|
push aArchiveDataError_ptr
|
|
|
|
|
push 1
|
|
|
|
|
call [SayErr]
|
|
|
|
|
.reterr:
|
|
|
|
|
or eax, -1
|
|
|
|
|
ret 12
|
|
|
|
|
|
|
|
|
|
; void __stdcall setpos(HANDLE hFile, __int64 pos);
|
|
|
|
|
setpos_7z:
|
|
|
|
|
cmp [ebx+file_handle_7z.context], 0
|
|
|
|
|
jz .ret
|
|
|
|
|
mov edi, [ebx+file_handle_7z.base]
|
|
|
|
|
mov ecx, [edi+handle_7z.host]
|
|
|
|
|
mov [inStream], ecx
|
|
|
|
|
mov [_esp], esp
|
|
|
|
|
mov [_ebp], ebp
|
|
|
|
|
mov [error_proc], read_7z.error
|
|
|
|
|
mov [clear_proc], read_7z.clear ; should not be called
|
|
|
|
|
cmp [ebx+file_handle_7z.bError], 0
|
|
|
|
|
jnz .backward ; if was error, force reinitialization
|
|
|
|
|
mov ecx, [esp+8]
|
|
|
|
|
mov edx, [esp+12]
|
|
|
|
|
sub ecx, dword [ebx+file_handle_7z.pos]
|
|
|
|
|
sbb edx, dword [ebx+file_handle_7z.pos+4]
|
|
|
|
|
jb .backward
|
|
|
|
|
; move forward - skip some data
|
|
|
|
|
mov eax, [ebx+file_handle_7z.mainStream]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
mov dword [eax+streamInfo.fullSize+4], edx
|
|
|
|
|
call skip_7z
|
|
|
|
|
add dword [ebx+file_handle_7z.pos], ecx
|
|
|
|
|
adc dword [ebx+file_handle_7z.pos], edx
|
|
|
|
|
.ret:
|
|
|
|
|
ret 12
|
|
|
|
|
.backward:
|
|
|
|
|
; move backward - reinitialize and skip start data
|
|
|
|
|
mov [ebx+file_handle_7z.bError], 0
|
|
|
|
|
mov ebp, [ebx+file_handle_7z.context]
|
|
|
|
|
mov eax, [ebx+file_handle_7z.item]
|
|
|
|
|
mov ebx, [edi+handle_7z.folders]
|
|
|
|
|
mov eax, [eax+file_in_7z.folder]
|
|
|
|
|
mov ebx, [ebx+eax*4]
|
|
|
|
|
; initialize streamInfos for decoders
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov esi, [ebx+_7z.StreamsInfo.unpackSizes]
|
|
|
|
|
@@:
|
|
|
|
|
lodsd
|
|
|
|
|
mov [ebp], eax
|
|
|
|
|
lodsd
|
|
|
|
|
mov [ebp+4], eax
|
|
|
|
|
and [ebp+streamInfo.bufDataLen], 0
|
|
|
|
|
push esi
|
|
|
|
|
mov eax, [ebx+_7z.StreamsInfo.fsz+ecx*4]
|
|
|
|
|
call _7z.GetCoder
|
|
|
|
|
movzx esi, byte [eax+4]
|
|
|
|
|
lea esi, [esi+eax+17]
|
|
|
|
|
push ebx ecx edi
|
|
|
|
|
mov bl, 1
|
|
|
|
|
call [_7z.InitTable+edx*4]
|
|
|
|
|
pop edi ecx ebx esi
|
|
|
|
|
mov edx, [ebp+streamInfo.bufSize]
|
|
|
|
|
mov ebp, [ebp+streamInfo.bufPtr]
|
|
|
|
|
add ebp, edx
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numCoders]
|
|
|
|
|
jb @b
|
|
|
|
|
; initialize streamInfos for input streams
|
|
|
|
|
xor ecx, ecx
|
|
|
|
|
mov esi, [ebx+_7z.StreamsInfo.startPackedStream]
|
|
|
|
|
shl esi, 3
|
|
|
|
|
add esi, [edi+handle_7z.packSizes]
|
|
|
|
|
mov edi, dword [ebx+_7z.StreamsInfo.packOffset]
|
|
|
|
|
mov edx, dword [ebx+_7z.StreamsInfo.packOffset+4]
|
|
|
|
|
@@:
|
|
|
|
|
mov dword [ebp+streamInfo.size], edi
|
|
|
|
|
mov dword [ebp+streamInfo.size+4], edx
|
|
|
|
|
and [ebp+streamInfo.bufDataLen], 0
|
|
|
|
|
lodsd
|
|
|
|
|
add edi, eax
|
|
|
|
|
mov [ebp], eax
|
|
|
|
|
lodsd
|
|
|
|
|
adc edx, eax
|
|
|
|
|
mov [ebp+4], eax
|
|
|
|
|
add ebp, 0x4000
|
|
|
|
|
inc ecx
|
|
|
|
|
cmp ecx, [ebx+_7z.StreamsInfo.numPackedStreams]
|
|
|
|
|
jb @b
|
|
|
|
|
mov ebx, [esp+4]
|
|
|
|
|
mov esi, [ebx+file_handle_7z.item]
|
|
|
|
|
mov eax, [ebx+file_handle_7z.mainStream]
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.folderStart]
|
|
|
|
|
add ecx, [esp+8]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize], ecx
|
|
|
|
|
mov ecx, dword [esi+file_in_7z.folderStart+4]
|
|
|
|
|
adc ecx, [esp+12]
|
|
|
|
|
mov dword [eax+streamInfo.fullSize+4], ecx
|
|
|
|
|
and dword [ebx+file_handle_7z.pos], 0
|
|
|
|
|
and dword [ebx+file_handle_7z.pos+4], 0
|
|
|
|
|
and [eax+streamInfo.bufDataLen], 0
|
|
|
|
|
call skip_7z
|
|
|
|
|
mov eax, [esp+8]
|
|
|
|
|
mov dword [ebx+file_handle_7z.pos], eax
|
|
|
|
|
mov eax, [esp+12]
|
|
|
|
|
mov dword [ebx+file_handle_7z.pos+4], eax
|
|
|
|
|
ret 12
|
|
|
|
|
|
|
|
|
|
close_file_7z:
|
|
|
|
|
mov ecx, [ebx+file_handle_7z.context]
|
|
|
|
|
jecxz .ret
|
|
|
|
|
cmp [ebx+file_handle_7z.bError], 0
|
|
|
|
|
jnz @f
|
|
|
|
|
push ebp
|
|
|
|
|
mov ebp, [ebx+file_handle_7z.base]
|
|
|
|
|
xchg ecx, [ebp+handle_7z.last_context]
|
|
|
|
|
mov eax, [ebx+file_handle_7z.item]
|
|
|
|
|
mov edx, [eax+file_in_7z.folder]
|
|
|
|
|
mov [ebp+handle_7z.last_folder], edx
|
|
|
|
|
mov edx, [ebx+file_handle_7z.mainStream]
|
|
|
|
|
mov [ebp+handle_7z.last_main_stream], edx
|
|
|
|
|
mov edx, dword [eax+file_in_7z.folderStart+4]
|
|
|
|
|
mov eax, dword [eax+file_in_7z.folderStart]
|
|
|
|
|
add eax, dword [ebx+file_handle_7z.pos]
|
|
|
|
|
adc edx, dword [ebx+file_handle_7z.pos+4]
|
|
|
|
|
mov dword [ebp+handle_7z.last_pos], eax
|
|
|
|
|
mov dword [ebp+handle_7z.last_pos+4], edx
|
|
|
|
|
pop ebp
|
|
|
|
|
@@:
|
|
|
|
|
jecxz @f
|
|
|
|
|
call [pgfree]
|
|
|
|
|
@@:
|
|
|
|
|
mov esi, ebx
|
|
|
|
|
call free_handle
|
|
|
|
|
.ret:
|
|
|
|
|
ret 4
|