From f1472e313401bcc589f60774b27216f99ced8c68 Mon Sep 17 00:00:00 2001 From: "jan.nijtmans" Date: Fri, 4 May 2012 21:11:58 +0000 Subject: some more removals from zlib1.2.7 FossilOrigin-Name: 0b062cab344e81e3deba45c6f85ea21fb56e0aa9 --- compat/zlib/contrib/asm586/README.586 | 43 ---- compat/zlib/contrib/asm586/match.S | 364 ------------------------------ compat/zlib/contrib/masm686/match.asm | 413 ---------------------------------- 3 files changed, 820 deletions(-) delete mode 100644 compat/zlib/contrib/asm586/README.586 delete mode 100644 compat/zlib/contrib/asm586/match.S delete mode 100644 compat/zlib/contrib/masm686/match.asm diff --git a/compat/zlib/contrib/asm586/README.586 b/compat/zlib/contrib/asm586/README.586 deleted file mode 100644 index 6bb78f3..0000000 --- a/compat/zlib/contrib/asm586/README.586 +++ /dev/null @@ -1,43 +0,0 @@ -This is a patched version of zlib modified to use -Pentium-optimized assembly code in the deflation algorithm. The files -changed/added by this patch are: - -README.586 -match.S - -The effectiveness of these modifications is a bit marginal, as the the -program's bottleneck seems to be mostly L1-cache contention, for which -there is no real way to work around without rewriting the basic -algorithm. The speedup on average is around 5-10% (which is generally -less than the amount of variance between subsequent executions). -However, when used at level 9 compression, the cache contention can -drop enough for the assembly version to achieve 10-20% speedup (and -sometimes more, depending on the amount of overall redundancy in the -files). Even here, though, cache contention can still be the limiting -factor, depending on the nature of the program using the zlib library. -This may also mean that better improvements will be seen on a Pentium -with MMX, which suffers much less from L1-cache contention, but I have -not yet verified this. - -Note that this code has been tailored for the Pentium in particular, -and will not perform well on the Pentium Pro (due to the use of a -partial register in the inner loop). - -If you are using an assembler other than GNU as, you will have to -translate match.S to use your assembler's syntax. (Have fun.) - -Brian Raiter -breadbox@muppetlabs.com -April, 1998 - - -Added for zlib 1.1.3: - -The patches come from -http://www.muppetlabs.com/~breadbox/software/assembly.html - -To compile zlib with this asm file, copy match.S to the zlib directory -then do: - -CFLAGS="-O3 -DASMV" ./configure -make OBJA=match.o diff --git a/compat/zlib/contrib/asm586/match.S b/compat/zlib/contrib/asm586/match.S deleted file mode 100644 index 0368b35..0000000 --- a/compat/zlib/contrib/asm586/match.S +++ /dev/null @@ -1,364 +0,0 @@ -/* match.s -- Pentium-optimized version of longest_match() - * Written for zlib 1.1.2 - * Copyright (C) 1998 Brian Raiter - * - * This is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License. - */ - -#ifndef NO_UNDERLINE -#define match_init _match_init -#define longest_match _longest_match -#endif - -#define MAX_MATCH (258) -#define MIN_MATCH (3) -#define MIN_LOOKAHEAD (MAX_MATCH + MIN_MATCH + 1) -#define MAX_MATCH_8 ((MAX_MATCH + 7) & ~7) - -/* stack frame offsets */ - -#define wmask 0 /* local copy of s->wmask */ -#define window 4 /* local copy of s->window */ -#define windowbestlen 8 /* s->window + bestlen */ -#define chainlenscanend 12 /* high word: current chain len */ - /* low word: last bytes sought */ -#define scanstart 16 /* first two bytes of string */ -#define scanalign 20 /* dword-misalignment of string */ -#define nicematch 24 /* a good enough match size */ -#define bestlen 28 /* size of best match so far */ -#define scan 32 /* ptr to string wanting match */ - -#define LocalVarsSize (36) -/* saved ebx 36 */ -/* saved edi 40 */ -/* saved esi 44 */ -/* saved ebp 48 */ -/* return address 52 */ -#define deflatestate 56 /* the function arguments */ -#define curmatch 60 - -/* Offsets for fields in the deflate_state structure. These numbers - * are calculated from the definition of deflate_state, with the - * assumption that the compiler will dword-align the fields. (Thus, - * changing the definition of deflate_state could easily cause this - * program to crash horribly, without so much as a warning at - * compile time. Sigh.) - */ - -/* All the +zlib1222add offsets are due to the addition of fields - * in zlib in the deflate_state structure since the asm code was first written - * (if you compile with zlib 1.0.4 or older, use "zlib1222add equ (-4)"). - * (if you compile with zlib between 1.0.5 and 1.2.2.1, use "zlib1222add equ 0"). - * if you compile with zlib 1.2.2.2 or later , use "zlib1222add equ 8"). - */ - -#define zlib1222add (8) - -#define dsWSize (36+zlib1222add) -#define dsWMask (44+zlib1222add) -#define dsWindow (48+zlib1222add) -#define dsPrev (56+zlib1222add) -#define dsMatchLen (88+zlib1222add) -#define dsPrevMatch (92+zlib1222add) -#define dsStrStart (100+zlib1222add) -#define dsMatchStart (104+zlib1222add) -#define dsLookahead (108+zlib1222add) -#define dsPrevLen (112+zlib1222add) -#define dsMaxChainLen (116+zlib1222add) -#define dsGoodMatch (132+zlib1222add) -#define dsNiceMatch (136+zlib1222add) - - -.file "match.S" - -.globl match_init, longest_match - -.text - -/* uInt longest_match(deflate_state *deflatestate, IPos curmatch) */ - -longest_match: - -/* Save registers that the compiler may be using, and adjust %esp to */ -/* make room for our stack frame. */ - - pushl %ebp - pushl %edi - pushl %esi - pushl %ebx - subl $LocalVarsSize, %esp - -/* Retrieve the function arguments. %ecx will hold cur_match */ -/* throughout the entire function. %edx will hold the pointer to the */ -/* deflate_state structure during the function's setup (before */ -/* entering the main loop). */ - - movl deflatestate(%esp), %edx - movl curmatch(%esp), %ecx - -/* if ((uInt)nice_match > s->lookahead) nice_match = s->lookahead; */ - - movl dsNiceMatch(%edx), %eax - movl dsLookahead(%edx), %ebx - cmpl %eax, %ebx - jl LookaheadLess - movl %eax, %ebx -LookaheadLess: movl %ebx, nicematch(%esp) - -/* register Bytef *scan = s->window + s->strstart; */ - - movl dsWindow(%edx), %esi - movl %esi, window(%esp) - movl dsStrStart(%edx), %ebp - lea (%esi,%ebp), %edi - movl %edi, scan(%esp) - -/* Determine how many bytes the scan ptr is off from being */ -/* dword-aligned. */ - - movl %edi, %eax - negl %eax - andl $3, %eax - movl %eax, scanalign(%esp) - -/* IPos limit = s->strstart > (IPos)MAX_DIST(s) ? */ -/* s->strstart - (IPos)MAX_DIST(s) : NIL; */ - - movl dsWSize(%edx), %eax - subl $MIN_LOOKAHEAD, %eax - subl %eax, %ebp - jg LimitPositive - xorl %ebp, %ebp -LimitPositive: - -/* unsigned chain_length = s->max_chain_length; */ -/* if (s->prev_length >= s->good_match) { */ -/* chain_length >>= 2; */ -/* } */ - - movl dsPrevLen(%edx), %eax - movl dsGoodMatch(%edx), %ebx - cmpl %ebx, %eax - movl dsMaxChainLen(%edx), %ebx - jl LastMatchGood - shrl $2, %ebx -LastMatchGood: - -/* chainlen is decremented once beforehand so that the function can */ -/* use the sign flag instead of the zero flag for the exit test. */ -/* It is then shifted into the high word, to make room for the scanend */ -/* scanend value, which it will always accompany. */ - - decl %ebx - shll $16, %ebx - -/* int best_len = s->prev_length; */ - - movl dsPrevLen(%edx), %eax - movl %eax, bestlen(%esp) - -/* Store the sum of s->window + best_len in %esi locally, and in %esi. */ - - addl %eax, %esi - movl %esi, windowbestlen(%esp) - -/* register ush scan_start = *(ushf*)scan; */ -/* register ush scan_end = *(ushf*)(scan+best_len-1); */ - - movw (%edi), %bx - movw %bx, scanstart(%esp) - movw -1(%edi,%eax), %bx - movl %ebx, chainlenscanend(%esp) - -/* Posf *prev = s->prev; */ -/* uInt wmask = s->w_mask; */ - - movl dsPrev(%edx), %edi - movl dsWMask(%edx), %edx - mov %edx, wmask(%esp) - -/* Jump into the main loop. */ - - jmp LoopEntry - -.balign 16 - -/* do { - * match = s->window + cur_match; - * if (*(ushf*)(match+best_len-1) != scan_end || - * *(ushf*)match != scan_start) continue; - * [...] - * } while ((cur_match = prev[cur_match & wmask]) > limit - * && --chain_length != 0); - * - * Here is the inner loop of the function. The function will spend the - * majority of its time in this loop, and majority of that time will - * be spent in the first ten instructions. - * - * Within this loop: - * %ebx = chainlenscanend - i.e., ((chainlen << 16) | scanend) - * %ecx = curmatch - * %edx = curmatch & wmask - * %esi = windowbestlen - i.e., (window + bestlen) - * %edi = prev - * %ebp = limit - * - * Two optimization notes on the choice of instructions: - * - * The first instruction uses a 16-bit address, which costs an extra, - * unpairable cycle. This is cheaper than doing a 32-bit access and - * zeroing the high word, due to the 3-cycle misalignment penalty which - * would occur half the time. This also turns out to be cheaper than - * doing two separate 8-bit accesses, as the memory is so rarely in the - * L1 cache. - * - * The window buffer, however, apparently spends a lot of time in the - * cache, and so it is faster to retrieve the word at the end of the - * match string with two 8-bit loads. The instructions that test the - * word at the beginning of the match string, however, are executed - * much less frequently, and there it was cheaper to use 16-bit - * instructions, which avoided the necessity of saving off and - * subsequently reloading one of the other registers. - */ -LookupLoop: - /* 1 U & V */ - movw (%edi,%edx,2), %cx /* 2 U pipe */ - movl wmask(%esp), %edx /* 2 V pipe */ - cmpl %ebp, %ecx /* 3 U pipe */ - jbe LeaveNow /* 3 V pipe */ - subl $0x00010000, %ebx /* 4 U pipe */ - js LeaveNow /* 4 V pipe */ -LoopEntry: movb -1(%esi,%ecx), %al /* 5 U pipe */ - andl %ecx, %edx /* 5 V pipe */ - cmpb %bl, %al /* 6 U pipe */ - jnz LookupLoop /* 6 V pipe */ - movb (%esi,%ecx), %ah - cmpb %bh, %ah - jnz LookupLoop - movl window(%esp), %eax - movw (%eax,%ecx), %ax - cmpw scanstart(%esp), %ax - jnz LookupLoop - -/* Store the current value of chainlen. */ - - movl %ebx, chainlenscanend(%esp) - -/* Point %edi to the string under scrutiny, and %esi to the string we */ -/* are hoping to match it up with. In actuality, %esi and %edi are */ -/* both pointed (MAX_MATCH_8 - scanalign) bytes ahead, and %edx is */ -/* initialized to -(MAX_MATCH_8 - scanalign). */ - - movl window(%esp), %esi - movl scan(%esp), %edi - addl %ecx, %esi - movl scanalign(%esp), %eax - movl $(-MAX_MATCH_8), %edx - lea MAX_MATCH_8(%edi,%eax), %edi - lea MAX_MATCH_8(%esi,%eax), %esi - -/* Test the strings for equality, 8 bytes at a time. At the end, - * adjust %edx so that it is offset to the exact byte that mismatched. - * - * We already know at this point that the first three bytes of the - * strings match each other, and they can be safely passed over before - * starting the compare loop. So what this code does is skip over 0-3 - * bytes, as much as necessary in order to dword-align the %edi - * pointer. (%esi will still be misaligned three times out of four.) - * - * It should be confessed that this loop usually does not represent - * much of the total running time. Replacing it with a more - * straightforward "rep cmpsb" would not drastically degrade - * performance. - */ -LoopCmps: - movl (%esi,%edx), %eax - movl (%edi,%edx), %ebx - xorl %ebx, %eax - jnz LeaveLoopCmps - movl 4(%esi,%edx), %eax - movl 4(%edi,%edx), %ebx - xorl %ebx, %eax - jnz LeaveLoopCmps4 - addl $8, %edx - jnz LoopCmps - jmp LenMaximum -LeaveLoopCmps4: addl $4, %edx -LeaveLoopCmps: testl $0x0000FFFF, %eax - jnz LenLower - addl $2, %edx - shrl $16, %eax -LenLower: subb $1, %al - adcl $0, %edx - -/* Calculate the length of the match. If it is longer than MAX_MATCH, */ -/* then automatically accept it as the best possible match and leave. */ - - lea (%edi,%edx), %eax - movl scan(%esp), %edi - subl %edi, %eax - cmpl $MAX_MATCH, %eax - jge LenMaximum - -/* If the length of the match is not longer than the best match we */ -/* have so far, then forget it and return to the lookup loop. */ - - movl deflatestate(%esp), %edx - movl bestlen(%esp), %ebx - cmpl %ebx, %eax - jg LongerMatch - movl chainlenscanend(%esp), %ebx - movl windowbestlen(%esp), %esi - movl dsPrev(%edx), %edi - movl wmask(%esp), %edx - andl %ecx, %edx - jmp LookupLoop - -/* s->match_start = cur_match; */ -/* best_len = len; */ -/* if (len >= nice_match) break; */ -/* scan_end = *(ushf*)(scan+best_len-1); */ - -LongerMatch: movl nicematch(%esp), %ebx - movl %eax, bestlen(%esp) - movl %ecx, dsMatchStart(%edx) - cmpl %ebx, %eax - jge LeaveNow - movl window(%esp), %esi - addl %eax, %esi - movl %esi, windowbestlen(%esp) - movl chainlenscanend(%esp), %ebx - movw -1(%edi,%eax), %bx - movl dsPrev(%edx), %edi - movl %ebx, chainlenscanend(%esp) - movl wmask(%esp), %edx - andl %ecx, %edx - jmp LookupLoop - -/* Accept the current string, with the maximum possible length. */ - -LenMaximum: movl deflatestate(%esp), %edx - movl $MAX_MATCH, bestlen(%esp) - movl %ecx, dsMatchStart(%edx) - -/* if ((uInt)best_len <= s->lookahead) return (uInt)best_len; */ -/* return s->lookahead; */ - -LeaveNow: - movl deflatestate(%esp), %edx - movl bestlen(%esp), %ebx - movl dsLookahead(%edx), %eax - cmpl %eax, %ebx - jg LookaheadRet - movl %ebx, %eax -LookaheadRet: - -/* Restore the stack and return from whence we came. */ - - addl $LocalVarsSize, %esp - popl %ebx - popl %esi - popl %edi - popl %ebp -match_init: ret diff --git a/compat/zlib/contrib/masm686/match.asm b/compat/zlib/contrib/masm686/match.asm deleted file mode 100644 index 4b03a71..0000000 --- a/compat/zlib/contrib/masm686/match.asm +++ /dev/null @@ -1,413 +0,0 @@ - -; match.asm -- Pentium-Pro optimized version of longest_match() -; -; Updated for zlib 1.1.3 and converted to MASM 6.1x -; Copyright (C) 2000 Dan Higdon -; and Chuck Walbourn -; Corrections by Cosmin Truta -; -; This is free software; you can redistribute it and/or modify it -; under the terms of the GNU General Public License. - -; Based on match.S -; Written for zlib 1.1.2 -; Copyright (C) 1998 Brian Raiter -; -; Modified by Gilles Vollant (2005) for add gzhead and gzindex - - .686P - .MODEL FLAT - -;=========================================================================== -; EQUATES -;=========================================================================== - -MAX_MATCH EQU 258 -MIN_MATCH EQU 3 -MIN_LOOKAHEAD EQU (MAX_MATCH + MIN_MATCH + 1) -MAX_MATCH_8 EQU ((MAX_MATCH + 7) AND (NOT 7)) - -;=========================================================================== -; STRUCTURES -;=========================================================================== - -; This STRUCT assumes a 4-byte alignment - -DEFLATE_STATE STRUCT -ds_strm dd ? -ds_status dd ? -ds_pending_buf dd ? -ds_pending_buf_size dd ? -ds_pending_out dd ? -ds_pending dd ? -ds_wrap dd ? -; gzhead and gzindex are added in zlib 1.2.2.2 (see deflate.h) -ds_gzhead dd ? -ds_gzindex dd ? -ds_data_type db ? -ds_method db ? - db ? ; padding - db ? ; padding -ds_last_flush dd ? -ds_w_size dd ? ; used -ds_w_bits dd ? -ds_w_mask dd ? ; used -ds_window dd ? ; used -ds_window_size dd ? -ds_prev dd ? ; used -ds_head dd ? -ds_ins_h dd ? -ds_hash_size dd ? -ds_hash_bits dd ? -ds_hash_mask dd ? -ds_hash_shift dd ? -ds_block_start dd ? -ds_match_length dd ? ; used -ds_prev_match dd ? ; used -ds_match_available dd ? -ds_strstart dd ? ; used -ds_match_start dd ? ; used -ds_lookahead dd ? ; used -ds_prev_length dd ? ; used -ds_max_chain_length dd ? ; used -ds_max_laxy_match dd ? -ds_level dd ? -ds_strategy dd ? -ds_good_match dd ? ; used -ds_nice_match dd ? ; used - -; Don't need anymore of the struct for match -DEFLATE_STATE ENDS - -;=========================================================================== -; CODE -;=========================================================================== -_TEXT SEGMENT - -;--------------------------------------------------------------------------- -; match_init -;--------------------------------------------------------------------------- - ALIGN 4 -PUBLIC _match_init -_match_init PROC - ; no initialization needed - ret -_match_init ENDP - -;--------------------------------------------------------------------------- -; uInt longest_match(deflate_state *deflatestate, IPos curmatch) -;--------------------------------------------------------------------------- - ALIGN 4 - -PUBLIC _longest_match -_longest_match PROC - -; Since this code uses EBP for a scratch register, the stack frame must -; be manually constructed and referenced relative to the ESP register. - -; Stack image -; Variables -chainlenwmask = 0 ; high word: current chain len - ; low word: s->wmask -window = 4 ; local copy of s->window -windowbestlen = 8 ; s->window + bestlen -scanend = 12 ; last two bytes of string -scanstart = 16 ; first two bytes of string -scanalign = 20 ; dword-misalignment of string -nicematch = 24 ; a good enough match size -bestlen = 28 ; size of best match so far -scan = 32 ; ptr to string wanting match -varsize = 36 ; number of bytes (also offset to last saved register) - -; Saved Registers (actually pushed into place) -ebx_save = 36 -edi_save = 40 -esi_save = 44 -ebp_save = 48 - -; Parameters -retaddr = 52 -deflatestate = 56 -curmatch = 60 - -; Save registers that the compiler may be using - push ebp - push edi - push esi - push ebx - -; Allocate local variable space - sub esp,varsize - -; Retrieve the function arguments. ecx will hold cur_match -; throughout the entire function. edx will hold the pointer to the -; deflate_state structure during the function's setup (before -; entering the main loop). - - mov edx, [esp+deflatestate] -ASSUME edx:PTR DEFLATE_STATE - - mov ecx, [esp+curmatch] - -; uInt wmask = s->w_mask; -; unsigned chain_length = s->max_chain_length; -; if (s->prev_length >= s->good_match) { -; chain_length >>= 2; -; } - - mov eax, [edx].ds_prev_length - mov ebx, [edx].ds_good_match - cmp eax, ebx - mov eax, [edx].ds_w_mask - mov ebx, [edx].ds_max_chain_length - jl SHORT LastMatchGood - shr ebx, 2 -LastMatchGood: - -; chainlen is decremented once beforehand so that the function can -; use the sign flag instead of the zero flag for the exit test. -; It is then shifted into the high word, to make room for the wmask -; value, which it will always accompany. - - dec ebx - shl ebx, 16 - or ebx, eax - mov [esp+chainlenwmask], ebx - -; if ((uInt)nice_match > s->lookahead) nice_match = s->lookahead; - - mov eax, [edx].ds_nice_match - mov ebx, [edx].ds_lookahead - cmp ebx, eax - jl SHORT LookaheadLess - mov ebx, eax -LookaheadLess: - mov [esp+nicematch], ebx - -;/* register Bytef *scan = s->window + s->strstart; */ - - mov esi, [edx].ds_window - mov [esp+window], esi - mov ebp, [edx].ds_strstart - lea edi, [esi+ebp] - mov [esp+scan],edi - -;/* Determine how many bytes the scan ptr is off from being */ -;/* dword-aligned. */ - - mov eax, edi - neg eax - and eax, 3 - mov [esp+scanalign], eax - -;/* IPos limit = s->strstart > (IPos)MAX_DIST(s) ? */ -;/* s->strstart - (IPos)MAX_DIST(s) : NIL; */ - - mov eax, [edx].ds_w_size - sub eax, MIN_LOOKAHEAD - sub ebp, eax - jg SHORT LimitPositive - xor ebp, ebp -LimitPositive: - -;/* int best_len = s->prev_length; */ - - mov eax, [edx].ds_prev_length - mov [esp+bestlen], eax - -;/* Store the sum of s->window + best_len in %esi locally, and in %esi. */ - - add esi, eax - mov [esp+windowbestlen], esi - -;/* register ush scan_start = *(ushf*)scan; */ -;/* register ush scan_end = *(ushf*)(scan+best_len-1); */ -;/* Posf *prev = s->prev; */ - - movzx ebx, WORD PTR[edi] - mov [esp+scanstart], ebx - movzx ebx, WORD PTR[eax+edi-1] - mov [esp+scanend], ebx - mov edi, [edx].ds_prev - -;/* Jump into the main loop. */ - - mov edx, [esp+chainlenwmask] - jmp SHORT LoopEntry - -;/* do { -; * match = s->window + cur_match; -; * if (*(ushf*)(match+best_len-1) != scan_end || -; * *(ushf*)match != scan_start) continue; -; * [...] -; * } while ((cur_match = prev[cur_match & wmask]) > limit -; * && --chain_length != 0); -; * -; * Here is the inner loop of the function. The function will spend the -; * majority of its time in this loop, and majority of that time will -; * be spent in the first ten instructions. -; * -; * Within this loop: -; * %ebx = scanend -; * %ecx = curmatch -; * %edx = chainlenwmask - i.e., ((chainlen << 16) | wmask) -; * %esi = windowbestlen - i.e., (window + bestlen) -; * %edi = prev -; * %ebp = limit -; */ - - ALIGN 4 -LookupLoop: - and ecx, edx - movzx ecx, WORD PTR[edi+ecx*2] - cmp ecx, ebp - jbe LeaveNow - sub edx, 000010000H - js LeaveNow - -LoopEntry: - movzx eax, WORD PTR[esi+ecx-1] - cmp eax, ebx - jnz SHORT LookupLoop - - mov eax, [esp+window] - movzx eax, WORD PTR[eax+ecx] - cmp eax, [esp+scanstart] - jnz SHORT LookupLoop - -;/* Store the current value of chainlen. */ - - mov [esp+chainlenwmask], edx - -;/* Point %edi to the string under scrutiny, and %esi to the string we */ -;/* are hoping to match it up with. In actuality, %esi and %edi are */ -;/* both pointed (MAX_MATCH_8 - scanalign) bytes ahead, and %edx is */ -;/* initialized to -(MAX_MATCH_8 - scanalign). */ - - mov esi, [esp+window] - mov edi, [esp+scan] - add esi, ecx - mov eax, [esp+scanalign] - mov edx, -MAX_MATCH_8 - lea edi, [edi+eax+MAX_MATCH_8] - lea esi, [esi+eax+MAX_MATCH_8] - -;/* Test the strings for equality, 8 bytes at a time. At the end, -; * adjust %edx so that it is offset to the exact byte that mismatched. -; * -; * We already know at this point that the first three bytes of the -; * strings match each other, and they can be safely passed over before -; * starting the compare loop. So what this code does is skip over 0-3 -; * bytes, as much as necessary in order to dword-align the %edi -; * pointer. (%esi will still be misaligned three times out of four.) -; * -; * It should be confessed that this loop usually does not represent -; * much of the total running time. Replacing it with a more -; * straightforward "rep cmpsb" would not drastically degrade -; * performance. -; */ - -LoopCmps: - mov eax, DWORD PTR[esi+edx] - xor eax, DWORD PTR[edi+edx] - jnz SHORT LeaveLoopCmps - - mov eax, DWORD PTR[esi+edx+4] - xor eax, DWORD PTR[edi+edx+4] - jnz SHORT LeaveLoopCmps4 - - add edx, 8 - jnz SHORT LoopCmps - jmp LenMaximum - ALIGN 4 - -LeaveLoopCmps4: - add edx, 4 - -LeaveLoopCmps: - test eax, 00000FFFFH - jnz SHORT LenLower - - add edx, 2 - shr eax, 16 - -LenLower: - sub al, 1 - adc edx, 0 - -;/* Calculate the length of the match. If it is longer than MAX_MATCH, */ -;/* then automatically accept it as the best possible match and leave. */ - - lea eax, [edi+edx] - mov edi, [esp+scan] - sub eax, edi - cmp eax, MAX_MATCH - jge SHORT LenMaximum - -;/* If the length of the match is not longer than the best match we */ -;/* have so far, then forget it and return to the lookup loop. */ - - mov edx, [esp+deflatestate] - mov ebx, [esp+bestlen] - cmp eax, ebx - jg SHORT LongerMatch - mov esi, [esp+windowbestlen] - mov edi, [edx].ds_prev - mov ebx, [esp+scanend] - mov edx, [esp+chainlenwmask] - jmp LookupLoop - ALIGN 4 - -;/* s->match_start = cur_match; */ -;/* best_len = len; */ -;/* if (len >= nice_match) break; */ -;/* scan_end = *(ushf*)(scan+best_len-1); */ - -LongerMatch: - mov ebx, [esp+nicematch] - mov [esp+bestlen], eax - mov [edx].ds_match_start, ecx - cmp eax, ebx - jge SHORT LeaveNow - mov esi, [esp+window] - add esi, eax - mov [esp+windowbestlen], esi - movzx ebx, WORD PTR[edi+eax-1] - mov edi, [edx].ds_prev - mov [esp+scanend], ebx - mov edx, [esp+chainlenwmask] - jmp LookupLoop - ALIGN 4 - -;/* Accept the current string, with the maximum possible length. */ - -LenMaximum: - mov edx, [esp+deflatestate] - mov DWORD PTR[esp+bestlen], MAX_MATCH - mov [edx].ds_match_start, ecx - -;/* if ((uInt)best_len <= s->lookahead) return (uInt)best_len; */ -;/* return s->lookahead; */ - -LeaveNow: - mov edx, [esp+deflatestate] - mov ebx, [esp+bestlen] - mov eax, [edx].ds_lookahead - cmp ebx, eax - jg SHORT LookaheadRet - mov eax, ebx -LookaheadRet: - -; Restore the stack and return from whence we came. - - add esp, varsize - pop ebx - pop esi - pop edi - pop ebp - ret - -_longest_match ENDP - -_TEXT ENDS -END -- cgit v0.12