summaryrefslogtreecommitdiff
path: root/contrib/vstudio/vc70_32/gvmat32c.c
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/vstudio/vc70_32/gvmat32c.c')
-rw-r--r--contrib/vstudio/vc70_32/gvmat32c.c209
1 files changed, 209 insertions, 0 deletions
diff --git a/contrib/vstudio/vc70_32/gvmat32c.c b/contrib/vstudio/vc70_32/gvmat32c.c
new file mode 100644
index 0000000..38be10b
--- /dev/null
+++ b/contrib/vstudio/vc70_32/gvmat32c.c
@@ -0,0 +1,209 @@
1/* gvmat32.c -- C portion of the optimized longest_match for 32 bits x86
2 * Copyright (C) 1995-1996 Jean-loup Gailly and Gilles Vollant.
3 * File written by Gilles Vollant, by modifiying the longest_match
4 * from Jean-loup Gailly in deflate.c
5 * it prepare all parameters and call the assembly longest_match_gvasm
6 * longest_match execute standard C code is wmask != 0x7fff
7 * (assembly code is faster with a fixed wmask)
8 *
9 */
10
11#include "deflate.h"
12
13#undef FAR
14//#include <windows.h>
15
16#ifdef ASMV
17#define NIL 0
18
19#define UNALIGNED_OK
20
21
22/* if your C compiler don't add underline before function name,
23 define ADD_UNDERLINE_ASMFUNC */
24#ifdef ADD_UNDERLINE_ASMFUNC
25#define longest_match_7fff _longest_match_7fff
26#define longest_match_686 _longest_match_686
27#define cpudetect32 _cpudetect32
28#endif
29
30
31
32void match_init()
33{
34}
35
36unsigned long cpudetect32();
37
38uInt longest_match_c(
39 deflate_state *s,
40 IPos cur_match); /* current match */
41
42
43uInt longest_match_7fff(
44 deflate_state *s,
45 IPos cur_match); /* current match */
46
47uInt longest_match_686(
48 deflate_state *s,
49 IPos cur_match); /* current match */
50
51uInt longest_match(
52 deflate_state *s,
53 IPos cur_match) /* current match */
54{
55 static uInt iIsPPro=2;
56
57 if ((s->w_mask == 0x7fff) && (iIsPPro==0))
58 return longest_match_7fff(s,cur_match);
59
60 if (iIsPPro==1)
61 return longest_match_686(s,cur_match);
62
63 if (iIsPPro==2)
64 iIsPPro = (((cpudetect32()/0x100)&0xf)>=6) ? 1 : 0;
65
66 return longest_match_c(s,cur_match);
67}
68
69
70
71uInt longest_match_c(s, cur_match)
72 deflate_state *s;
73 IPos cur_match; /* current match */
74{
75 unsigned chain_length = s->max_chain_length;/* max hash chain length */
76 register Bytef *scan = s->window + s->strstart; /* current string */
77 register Bytef *match; /* matched string */
78 register int len; /* length of current match */
79 int best_len = s->prev_length; /* best match length so far */
80 int nice_match = s->nice_match; /* stop if match long enough */
81 IPos limit = s->strstart > (IPos)MAX_DIST(s) ?
82 s->strstart - (IPos)MAX_DIST(s) : NIL;
83 /* Stop when cur_match becomes <= limit. To simplify the code,
84 * we prevent matches with the string of window index 0.
85 */
86 Posf *prev = s->prev;
87 uInt wmask = s->w_mask;
88
89#ifdef UNALIGNED_OK
90 /* Compare two bytes at a time. Note: this is not always beneficial.
91 * Try with and without -DUNALIGNED_OK to check.
92 */
93 register Bytef *strend = s->window + s->strstart + MAX_MATCH - 1;
94 register ush scan_start = *(ushf*)scan;
95 register ush scan_end = *(ushf*)(scan+best_len-1);
96#else
97 register Bytef *strend = s->window + s->strstart + MAX_MATCH;
98 register Byte scan_end1 = scan[best_len-1];
99 register Byte scan_end = scan[best_len];
100#endif
101
102 /* The code is optimized for HASH_BITS >= 8 and MAX_MATCH-2 multiple of 16.
103 * It is easy to get rid of this optimization if necessary.
104 */
105 Assert(s->hash_bits >= 8 && MAX_MATCH == 258, "Code too clever");
106
107 /* Do not waste too much time if we already have a good match: */
108 if (s->prev_length >= s->good_match) {
109 chain_length >>= 2;
110 }
111 /* Do not look for matches beyond the end of the input. This is necessary
112 * to make deflate deterministic.
113 */
114 if ((uInt)nice_match > s->lookahead) nice_match = s->lookahead;
115
116 Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, "need lookahead");
117
118 do {
119 Assert(cur_match < s->strstart, "no future");
120 match = s->window + cur_match;
121
122 /* Skip to next match if the match length cannot increase
123 * or if the match length is less than 2:
124 */
125#if (defined(UNALIGNED_OK) && MAX_MATCH == 258)
126 /* This code assumes sizeof(unsigned short) == 2. Do not use
127 * UNALIGNED_OK if your compiler uses a different size.
128 */
129 if (*(ushf*)(match+best_len-1) != scan_end ||
130 *(ushf*)match != scan_start) continue;
131
132 /* It is not necessary to compare scan[2] and match[2] since they are
133 * always equal when the other bytes match, given that the hash keys
134 * are equal and that HASH_BITS >= 8. Compare 2 bytes at a time at
135 * strstart+3, +5, ... up to strstart+257. We check for insufficient
136 * lookahead only every 4th comparison; the 128th check will be made
137 * at strstart+257. If MAX_MATCH-2 is not a multiple of 8, it is
138 * necessary to put more guard bytes at the end of the window, or
139 * to check more often for insufficient lookahead.
140 */
141 Assert(scan[2] == match[2], "scan[2]?");
142 scan++, match++;
143 do {
144 } while (*(ushf*)(scan+=2) == *(ushf*)(match+=2) &&
145 *(ushf*)(scan+=2) == *(ushf*)(match+=2) &&
146 *(ushf*)(scan+=2) == *(ushf*)(match+=2) &&
147 *(ushf*)(scan+=2) == *(ushf*)(match+=2) &&
148 scan < strend);
149 /* The funny "do {}" generates better code on most compilers */
150
151 /* Here, scan <= window+strstart+257 */
152 Assert(scan <= s->window+(unsigned)(s->window_size-1), "wild scan");
153 if (*scan == *match) scan++;
154
155 len = (MAX_MATCH - 1) - (int)(strend-scan);
156 scan = strend - (MAX_MATCH-1);
157
158#else /* UNALIGNED_OK */
159
160 if (match[best_len] != scan_end ||
161 match[best_len-1] != scan_end1 ||
162 *match != *scan ||
163 *++match != scan[1]) continue;
164
165 /* The check at best_len-1 can be removed because it will be made
166 * again later. (This heuristic is not always a win.)
167 * It is not necessary to compare scan[2] and match[2] since they
168 * are always equal when the other bytes match, given that
169 * the hash keys are equal and that HASH_BITS >= 8.
170 */
171 scan += 2, match++;
172 Assert(*scan == *match, "match[2]?");
173
174 /* We check for insufficient lookahead only every 8th comparison;
175 * the 256th check will be made at strstart+258.
176 */
177 do {
178 } while (*++scan == *++match && *++scan == *++match &&
179 *++scan == *++match && *++scan == *++match &&
180 *++scan == *++match && *++scan == *++match &&
181 *++scan == *++match && *++scan == *++match &&
182 scan < strend);
183
184 Assert(scan <= s->window+(unsigned)(s->window_size-1), "wild scan");
185
186 len = MAX_MATCH - (int)(strend - scan);
187 scan = strend - MAX_MATCH;
188
189#endif /* UNALIGNED_OK */
190
191 if (len > best_len) {
192 s->match_start = cur_match;
193 best_len = len;
194 if (len >= nice_match) break;
195#ifdef UNALIGNED_OK
196 scan_end = *(ushf*)(scan+best_len-1);
197#else
198 scan_end1 = scan[best_len-1];
199 scan_end = scan[best_len];
200#endif
201 }
202 } while ((cur_match = prev[cur_match & wmask]) > limit
203 && --chain_length != 0);
204
205 if ((uInt)best_len <= s->lookahead) return (uInt)best_len;
206 return s->lookahead;
207}
208
209#endif /* ASMV */