Subversion Repositories Kolibri OS

Rev

Rev 6799 | Rev 6815 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 6799 Rev 6813
1
; trees.asm -- output deflated data using Huffman coding
1
; trees.asm -- output deflated data using Huffman coding
2
; Copyright (C) 1995-2012 Jean-loup Gailly
2
; Copyright (C) 1995-2012 Jean-loup Gailly
3
; detect_data_type() function provided freely by Cosmin Truta, 2006
3
; detect_data_type() function provided freely by Cosmin Truta, 2006
4
; For conditions of distribution and use, see copyright notice in zlib.h
4
; For conditions of distribution and use, see copyright notice in zlib.h
5
 
5
 
6
;  ALGORITHM
6
;  ALGORITHM
7
 
7
 
8
;      The "deflation" process uses several Huffman trees. The more
8
;      The "deflation" process uses several Huffman trees. The more
9
;      common source values are represented by shorter bit sequences.
9
;      common source values are represented by shorter bit sequences.
10
 
10
 
11
;      Each code tree is stored in a compressed form which is itself
11
;      Each code tree is stored in a compressed form which is itself
12
; a Huffman encoding of the lengths of all the code strings (in
12
; a Huffman encoding of the lengths of all the code strings (in
13
; ascending order by source values).  The actual code strings are
13
; ascending order by source values).  The actual code strings are
14
; reconstructed from the lengths in the inflate process, as described
14
; reconstructed from the lengths in the inflate process, as described
15
; in the deflate specification.
15
; in the deflate specification.
16
 
16
 
17
;  REFERENCES
17
;  REFERENCES
18
 
18
 
19
;      Deutsch, L.P.,"'Deflate' Compressed Data Format Specification".
19
;      Deutsch, L.P.,"'Deflate' Compressed Data Format Specification".
20
;      Available in ftp.uu.net:/pub/archiving/zip/doc/deflate-1.1.doc
20
;      Available in ftp.uu.net:/pub/archiving/zip/doc/deflate-1.1.doc
21
 
21
 
22
;      Storer, James A.
22
;      Storer, James A.
23
;          Data Compression:  Methods and Theory, pp. 49-50.
23
;          Data Compression:  Methods and Theory, pp. 49-50.
24
;          Computer Science Press, 1988.  ISBN 0-7167-8156-5.
24
;          Computer Science Press, 1988.  ISBN 0-7167-8156-5.
25
 
25
 
26
;      Sedgewick, R.
26
;      Sedgewick, R.
27
;          Algorithms, p290.
27
;          Algorithms, p290.
28
;          Addison-Wesley, 1983. ISBN 0-201-06672-6.
28
;          Addison-Wesley, 1983. ISBN 0-201-06672-6.
29
 
29
 
30
; ===========================================================================
30
; ===========================================================================
31
; Constants
31
; Constants
32
 
32
 
33
 
33
 
34
MAX_BL_BITS equ 7
34
MAX_BL_BITS equ 7
35
; Bit length codes must not exceed MAX_BL_BITS bits
35
; Bit length codes must not exceed MAX_BL_BITS bits
36
 
36
 
37
END_BLOCK equ 256
37
END_BLOCK equ 256
38
; end of block literal code
38
; end of block literal code
39
 
39
 
40
REP_3_6     equ 16
40
REP_3_6     equ 16
41
; repeat previous bit length 3-6 times (2 bits of repeat count)
41
; repeat previous bit length 3-6 times (2 bits of repeat count)
42
 
42
 
43
REPZ_3_10   equ 17
43
REPZ_3_10   equ 17
44
; repeat a zero length 3-10 times  (3 bits of repeat count)
44
; repeat a zero length 3-10 times  (3 bits of repeat count)
45
 
45
 
46
REPZ_11_138 equ 18
46
REPZ_11_138 equ 18
47
; repeat a zero length 11-138 times  (7 bits of repeat count)
47
; repeat a zero length 11-138 times  (7 bits of repeat count)
48
 
48
 
49
align 4
49
align 4
50
extra_lbits dd \ ;int [LENGTH_CODES] ;extra bits for each length code
50
extra_lbits dd \ ;int [LENGTH_CODES] ;extra bits for each length code
51
	0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0
51
	0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0
52
 
52
 
53
align 4
53
align 4
54
extra_dbits dd \ ;int [D_CODES] ;extra bits for each distance code
54
extra_dbits dd \ ;int [D_CODES] ;extra bits for each distance code
55
	0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13
55
	0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13
56
 
56
 
57
align 4
57
align 4
58
extra_blbits dd \ ;int [BL_CODES] ;extra bits for each bit length code
58
extra_blbits dd \ ;int [BL_CODES] ;extra bits for each bit length code
59
	0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,7
59
	0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,7
60
 
60
 
61
align 4
61
align 4
62
bl_order db 16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15
62
bl_order db 16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15
63
; The lengths of the bit length codes are sent in order of decreasing
63
; The lengths of the bit length codes are sent in order of decreasing
64
; probability, to avoid transmitting the lengths for unused bit length codes.
64
; probability, to avoid transmitting the lengths for unused bit length codes.
65
 
65
 
66
 
66
 
67
; ===========================================================================
67
; ===========================================================================
68
; Local data. These are initialized only once.
68
; Local data. These are initialized only once.
69
 
69
 
70
 
70
 
71
DIST_CODE_LEN equ 512 ;see definition of array dist_code below
71
DIST_CODE_LEN equ 512 ;see definition of array dist_code below
72
 
72
 
73
if GEN_TREES_H eq 1 ;| !(STDC)
73
if GEN_TREES_H eq 1 ;| !(STDC)
74
; non ANSI compilers may not accept trees.inc
74
; non ANSI compilers may not accept trees.inc
75
 
75
 
76
align 4
76
align 4
77
static_ltree rb sizeof.ct_data * (L_CODES+2)
77
static_ltree rb sizeof.ct_data * (L_CODES+2)
78
; The static literal tree. Since the bit lengths are imposed, there is no
78
; The static literal tree. Since the bit lengths are imposed, there is no
79
; need for the L_CODES extra codes used during heap construction. However
79
; need for the L_CODES extra codes used during heap construction. However
80
; The codes 286 and 287 are needed to build a canonical tree (see _tr_init
80
; The codes 286 and 287 are needed to build a canonical tree (see _tr_init
81
; below).
81
; below).
82
 
82
 
83
align 4
83
align 4
84
static_dtree rb sizeof.ct_data * D_CODES
84
static_dtree rb sizeof.ct_data * D_CODES
85
; The static distance tree. (Actually a trivial tree since all codes use
85
; The static distance tree. (Actually a trivial tree since all codes use
86
; 5 bits.)
86
; 5 bits.)
87
 
87
 
88
align 4
88
align 4
89
_dist_code rb DIST_CODE_LEN ;uch[]
89
_dist_code rb DIST_CODE_LEN ;uch[]
90
; Distance codes. The first 256 values correspond to the distances
90
; Distance codes. The first 256 values correspond to the distances
91
; 3 .. 258, the last 256 values correspond to the top 8 bits of
91
; 3 .. 258, the last 256 values correspond to the top 8 bits of
92
; the 15 bit distances.
92
; the 15 bit distances.
93
 
93
 
94
align 4
94
align 4
95
_length_code rb MAX_MATCH-MIN_MATCH+1 ;uch[]
95
_length_code rb MAX_MATCH-MIN_MATCH+1 ;uch[]
96
; length code for each normalized match length (0 == MIN_MATCH)
96
; length code for each normalized match length (0 == MIN_MATCH)
97
 
97
 
98
align 4
98
align 4
99
base_length rd LENGTH_CODES ;int[]
99
base_length rd LENGTH_CODES ;int[]
100
; First normalized length for each code (0 = MIN_MATCH)
100
; First normalized length for each code (0 = MIN_MATCH)
101
 
101
 
102
align 4
102
align 4
103
base_dist rd D_CODES ;int[]
103
base_dist rd D_CODES ;int[]
104
; First normalized distance for each code (0 = distance of 1)
104
; First normalized distance for each code (0 = distance of 1)
105
 
105
 
106
else
106
else
107
include 'trees.inc'
107
include 'trees.inc'
108
end if ;GEN_TREES_H
108
end if ;GEN_TREES_H
109
 
109
 
110
struct static_tree_desc ;_s
110
struct static_tree_desc ;_s
111
	static_tree dd ? ;const ct_data * ;static tree or NULL
111
	static_tree dd ? ;const ct_data * ;static tree or NULL
112
	extra_bits  dd ? ;const intf * ;extra bits for each code or NULL
112
	extra_bits  dd ? ;const intf * ;extra bits for each code or NULL
113
	extra_base  dd ? ;int ;base index for extra_bits
113
	extra_base  dd ? ;int ;base index for extra_bits
114
	elems       dd ? ;int ;max number of elements in the tree
114
	elems       dd ? ;int ;max number of elements in the tree
115
	max_length  dd ? ;int ;max bit length for the codes
115
	max_length  dd ? ;int ;max bit length for the codes
116
ends
116
ends
117
 
117
 
118
align 4
118
align 4
119
static_l_desc static_tree_desc static_ltree, extra_lbits, LITERALS+1, L_CODES, MAX_BITS
119
static_l_desc static_tree_desc static_ltree, extra_lbits, LITERALS+1, L_CODES, MAX_BITS
120
 
120
 
121
align 4
121
align 4
122
static_d_desc static_tree_desc static_dtree, extra_dbits, 0, D_CODES, MAX_BITS
122
static_d_desc static_tree_desc static_dtree, extra_dbits, 0, D_CODES, MAX_BITS
123
 
123
 
124
align 4
124
align 4
125
static_bl_desc static_tree_desc 0, extra_blbits, 0, BL_CODES, MAX_BL_BITS
125
static_bl_desc static_tree_desc 0, extra_blbits, 0, BL_CODES, MAX_BL_BITS
126
 
126
 
127
; ===========================================================================
127
; ===========================================================================
128
; Local (static) routines in this file.
128
; Local (static) routines in this file.
129
 
129
 
130
 
130
 
131
macro send_code s, c, tree
131
macro send_code s, c, tree
132
{
132
{
133
if DEBUG eq 1
133
if DEBUG eq 1
134
;	if (z_verbose>2) fprintf(stderr,"\ncd %3d ",(c))
134
;	if (z_verbose>2) fprintf(stderr,"\ncd %3d ",(c))
135
end if
135
end if
136
push eax ebx
136
push eax ebx
137
if c eq eax
137
if c eq eax
138
else
138
else
139
	mov eax,c
139
	mov eax,c
140
end if
140
end if
141
	imul eax,sizeof.ct_data
141
	imul eax,sizeof.ct_data
142
	add eax,tree
142
	add eax,tree
143
	movzx ebx,word[eax+Len]
143
	movzx ebx,word[eax+Len]
144
	push ebx
144
	push ebx
145
	movzx ebx,word[eax+Code]
145
	movzx ebx,word[eax+Code]
146
	push ebx
146
	push ebx
147
	stdcall send_bits, s ;tree[c].Code, tree[c].Len
147
	stdcall send_bits, s ;tree[c].Code, tree[c].Len
148
pop ebx eax
148
pop ebx eax
149
}
149
}
150
; Send a code of the given tree[c] and tree must not have side effects
150
; Send a code of the given tree[c] and tree must not have side effects
151
 
151
 
152
; ===========================================================================
152
; ===========================================================================
153
; Output a short LSB first on the stream.
153
; Output a short LSB first on the stream.
154
; IN assertion: there is enough room in pendingBuf.
154
; IN assertion: there is enough room in pendingBuf.
155
 
155
 
156
macro put_short s, w
156
macro put_short s, w
157
{
157
{
158
	mov eax,[s+deflate_state.pending]
158
	mov eax,[s+deflate_state.pending]
159
	add eax,[s+deflate_state.pending_buf]
159
	add eax,[s+deflate_state.pending_buf]
160
	mov word[eax],w
160
	mov word[eax],w
161
	add dword[s+deflate_state.pending],2
161
	add dword[s+deflate_state.pending],2
162
}
162
}
163
 
163
 
164
; ===========================================================================
164
; ===========================================================================
165
; Send a value on a given number of bits.
165
; Send a value on a given number of bits.
166
; IN assertion: length <= 16 and value fits in length bits.
166
; IN assertion: length <= 16 and value fits in length bits.
167
 
167
 
168
;void (s, value, length)
168
;void (s, value, length)
169
;    deflate_state* s
169
;    deflate_state* s
170
;    int value  ;value to send
170
;    int value  ;value to send
171
;    int length ;number of bits
171
;    int length ;number of bits
172
align 4
172
align 4
173
proc send_bits uses eax ecx edi, s:dword, value:dword, length:dword
173
proc send_bits uses eax ecx edi, s:dword, value:dword, length:dword
174
;    Tracevv((stderr," l %2d v %4x ", length, value));
174
;    Tracevv((stderr," l %2d v %4x ", length, value));
175
	zlib_debug 'send_bits value = %d',[value]
175
	zlib_debug 'send_bits value = %d',[value]
176
;if DEBUG eq 1
176
;if DEBUG eq 1
177
	mov eax,[length]
177
	mov eax,[length]
178
	cmp eax,0
178
	cmp eax,0
179
	jle @f
179
	jle @f
180
	cmp eax,15
180
	cmp eax,15
181
	jle .end1
181
	jle .end1
182
	@@:
182
	@@:
183
		zlib_assert 'invalid length' ;Assert(..>0 && ..<=15)
183
		zlib_assert 'invalid length' ;Assert(..>0 && ..<=15)
184
	.end1:
184
	.end1:
185
	mov edi,[s]
185
	mov edi,[s]
186
	add [edi+deflate_state.bits_sent],eax
186
	add [edi+deflate_state.bits_sent],eax
187
 
187
 
188
	; If not enough room in bi_buf, use (valid) bits from bi_buf and
188
	; If not enough room in bi_buf, use (valid) bits from bi_buf and
189
	; (16 - bi_valid) bits from value, leaving (width - (16-bi_valid))
189
	; (16 - bi_valid) bits from value, leaving (width - (16-bi_valid))
190
	; unused bits in value.
190
	; unused bits in value.
191
 
191
 
192
	mov ecx,Buf_size
192
	mov ecx,Buf_size
193
	sub ecx,eax
193
	sub ecx,eax
194
	cmp [edi+deflate_state.bi_valid],ecx
194
	cmp [edi+deflate_state.bi_valid],ecx
195
	jle @f ;if (..>..)
195
	jle @f ;if (..>..)
196
		mov eax,[value]
196
		mov eax,[value]
197
		mov ecx,[edi+deflate_state.bi_valid]
197
		mov ecx,[edi+deflate_state.bi_valid]
198
		shl eax,cl
198
		shl eax,cl
199
		or [edi+deflate_state.bi_buf],ax
199
		or [edi+deflate_state.bi_buf],ax
200
		mov cx,[edi+deflate_state.bi_buf]
200
		mov cx,[edi+deflate_state.bi_buf]
201
		put_short edi, cx
201
		put_short edi, cx
202
		mov eax,[value]
202
		mov eax,[value]
203
		mov ecx,Buf_size
203
		mov ecx,Buf_size
204
		sub ecx,[edi+deflate_state.bi_valid]
204
		sub ecx,[edi+deflate_state.bi_valid]
205
		shr eax,cl
205
		shr eax,cl
206
		mov [edi+deflate_state.bi_buf],ax
206
		mov [edi+deflate_state.bi_buf],ax
207
		mov eax,[length]
207
		mov eax,[length]
208
		sub eax,Buf_size
208
		sub eax,Buf_size
209
		jmp .end0
209
		jmp .end0
210
	@@: ;else
210
	@@: ;else
211
		mov eax,[value]
211
		mov eax,[value]
212
		mov ecx,[edi+deflate_state.bi_valid]
212
		mov ecx,[edi+deflate_state.bi_valid]
213
		shl eax,cl
213
		shl eax,cl
214
		or [edi+deflate_state.bi_buf],ax
214
		or [edi+deflate_state.bi_buf],ax
215
		mov eax,[length]
215
		mov eax,[length]
216
	.end0:
216
	.end0:
217
	add [edi+deflate_state.bi_valid],eax
217
	add [edi+deflate_state.bi_valid],eax
218
;else ;!DEBUG
218
;else ;!DEBUG
219
 
219
 
220
;{ int len = length;
220
;{ int len = length;
221
;  if (s->bi_valid > (int)Buf_size - len) {
221
;  if (s->bi_valid > (int)Buf_size - len) {
222
;    int val = value;
222
;    int val = value;
223
;    s->bi_buf |= (uint_16)val << s->bi_valid;
223
;    s->bi_buf |= (uint_16)val << s->bi_valid;
224
;    put_short(s, s->bi_buf);
224
;    put_short(s, s->bi_buf);
225
;    s->bi_buf = (uint_16)val >> (Buf_size - s->bi_valid);
225
;    s->bi_buf = (uint_16)val >> (Buf_size - s->bi_valid);
226
;    s->bi_valid += len - Buf_size;
226
;    s->bi_valid += len - Buf_size;
227
;  } else {
227
;  } else {
228
;    s->bi_buf |= (uint_16)(value) << s->bi_valid;
228
;    s->bi_buf |= (uint_16)(value) << s->bi_valid;
229
;    s->bi_valid += len;
229
;    s->bi_valid += len;
230
;  }
230
;  }
231
;}
231
;}
232
;end if ;DEBUG
232
;end if ;DEBUG
233
	ret
233
	ret
234
endp
234
endp
235
 
235
 
236
; the arguments must not have side effects
236
; the arguments must not have side effects
237
 
237
 
238
; ===========================================================================
238
; ===========================================================================
239
; Initialize the various 'constant' tables.
239
; Initialize the various 'constant' tables.
240
 
240
 
241
;int static_init_done = 0
241
;int static_init_done = 0
242
 
242
 
243
;void ()
243
;void ()
244
align 4
244
align 4
245
proc tr_static_init
245
proc tr_static_init
246
if GEN_TREES_H eq 1
246
if GEN_TREES_H eq 1
247
 
247
 
248
;    int n      ;iterates over tree elements
248
;    int n      ;iterates over tree elements
249
;    int bits   ;bit counter
249
;    int bits   ;bit counter
250
;    int length ;length value
250
;    int length ;length value
251
;    int code   ;code value
251
;    int code   ;code value
252
;    int dist   ;distance index
252
;    int dist   ;distance index
253
;    uint_16 bl_count[MAX_BITS+1];
253
;    uint_16 bl_count[MAX_BITS+1];
254
	; number of codes at each bit length for an optimal tree
254
	; number of codes at each bit length for an optimal tree
255
 
255
 
256
;    if (static_init_done) return;
256
;    if (static_init_done) return;
257
 
257
 
258
	; For some embedded targets, global variables are not initialized:
258
	; For some embedded targets, global variables are not initialized:
259
;if NO_INIT_GLOBAL_POINTERS
259
;if NO_INIT_GLOBAL_POINTERS
260
;    static_l_desc.static_tree = static_ltree;
260
;    static_l_desc.static_tree = static_ltree;
261
;    static_l_desc.extra_bits = extra_lbits;
261
;    static_l_desc.extra_bits = extra_lbits;
262
;    static_d_desc.static_tree = static_dtree;
262
;    static_d_desc.static_tree = static_dtree;
263
;    static_d_desc.extra_bits = extra_dbits;
263
;    static_d_desc.extra_bits = extra_dbits;
264
;    static_bl_desc.extra_bits = extra_blbits;
264
;    static_bl_desc.extra_bits = extra_blbits;
265
;end if
265
;end if
266
 
266
 
267
	; Initialize the mapping length (0..255) -> length code (0..28)
267
	; Initialize the mapping length (0..255) -> length code (0..28)
268
;    length = 0;
268
;    length = 0;
269
;    for (code = 0; code < LENGTH_CODES-1; code++) {
269
;    for (code = 0; code < LENGTH_CODES-1; code++) {
270
;        base_length[code] = length;
270
;        base_length[code] = length;
271
;        for (n = 0; n < (1<
271
;        for (n = 0; n < (1<
272
;            _length_code[length++] = (uch)code;
272
;            _length_code[length++] = (uch)code;
273
;        }
273
;        }
274
;    }
274
;    }
275
;    Assert (length == 256, "tr_static_init: length != 256");
275
;    Assert (length == 256, "tr_static_init: length != 256");
276
	; Note that the length 255 (match length 258) can be represented
276
	; Note that the length 255 (match length 258) can be represented
277
	; in two different ways: code 284 + 5 bits or code 285, so we
277
	; in two different ways: code 284 + 5 bits or code 285, so we
278
	; overwrite length_code[255] to use the best encoding:
278
	; overwrite length_code[255] to use the best encoding:
279
 
279
 
280
;    _length_code[length-1] = (uch)code;
280
;    _length_code[length-1] = (uch)code;
281
 
281
 
282
	; Initialize the mapping dist (0..32K) -> dist code (0..29)
282
	; Initialize the mapping dist (0..32K) -> dist code (0..29)
283
;    dist = 0;
283
;    dist = 0;
284
;    for (code = 0 ; code < 16; code++) {
284
;    for (code = 0 ; code < 16; code++) {
285
;        base_dist[code] = dist;
285
;        base_dist[code] = dist;
286
;        for (n = 0; n < (1<
286
;        for (n = 0; n < (1<
287
;            _dist_code[dist++] = (uch)code;
287
;            _dist_code[dist++] = (uch)code;
288
;        }
288
;        }
289
;    }
289
;    }
290
;    Assert (dist == 256, "tr_static_init: dist != 256");
290
;    Assert (dist == 256, "tr_static_init: dist != 256");
291
;    dist >>= 7; /* from now on, all distances are divided by 128 */
291
;    dist >>= 7; /* from now on, all distances are divided by 128 */
292
;    for ( ; code < D_CODES; code++) {
292
;    for ( ; code < D_CODES; code++) {
293
;        base_dist[code] = dist << 7;
293
;        base_dist[code] = dist << 7;
294
;        for (n = 0; n < (1<<(extra_dbits[code]-7)); n++) {
294
;        for (n = 0; n < (1<<(extra_dbits[code]-7)); n++) {
295
;            _dist_code[256 + dist++] = (uch)code;
295
;            _dist_code[256 + dist++] = (uch)code;
296
;        }
296
;        }
297
;    }
297
;    }
298
;    Assert (dist == 256, "tr_static_init: 256+dist != 512");
298
;    Assert (dist == 256, "tr_static_init: 256+dist != 512");
299
 
299
 
300
	; Construct the codes of the static literal tree
300
	; Construct the codes of the static literal tree
301
;    for (bits = 0; bits <= MAX_BITS; bits++) bl_count[bits] = 0;
301
;    for (bits = 0; bits <= MAX_BITS; bits++) bl_count[bits] = 0;
302
;    n = 0;
302
;    n = 0;
303
;    while (n <= 143) static_ltree[n++].Len = 8, bl_count[8]++;
303
;    while (n <= 143) static_ltree[n++].Len = 8, bl_count[8]++;
304
;    while (n <= 255) static_ltree[n++].Len = 9, bl_count[9]++;
304
;    while (n <= 255) static_ltree[n++].Len = 9, bl_count[9]++;
305
;    while (n <= 279) static_ltree[n++].Len = 7, bl_count[7]++;
305
;    while (n <= 279) static_ltree[n++].Len = 7, bl_count[7]++;
306
;    while (n <= 287) static_ltree[n++].Len = 8, bl_count[8]++;
306
;    while (n <= 287) static_ltree[n++].Len = 8, bl_count[8]++;
307
	; Codes 286 and 287 do not exist, but we must include them in the
307
	; Codes 286 and 287 do not exist, but we must include them in the
308
	; tree construction to get a canonical Huffman tree (longest code
308
	; tree construction to get a canonical Huffman tree (longest code
309
	; all ones)
309
	; all ones)
310
 
310
 
311
;    gen_codes((ct_data *)static_ltree, L_CODES+1, bl_count);
311
;    gen_codes((ct_data *)static_ltree, L_CODES+1, bl_count);
312
 
312
 
313
	; The static distance tree is trivial:
313
	; The static distance tree is trivial:
314
;    for (n = 0; n < D_CODES; n++) {
314
;    for (n = 0; n < D_CODES; n++) {
315
;        static_dtree[n].Len = 5;
315
;        static_dtree[n].Len = 5;
316
;        static_dtree[n].Code = bi_reverse((unsigned)n, 5);
316
;        static_dtree[n].Code = bi_reverse((unsigned)n, 5);
317
;    }
317
;    }
318
;    static_init_done = 1;
318
;    static_init_done = 1;
319
 
319
 
320
if GEN_TREES_H eq 1
320
if GEN_TREES_H eq 1
321
	call gen_trees_header
321
	call gen_trees_header
322
end if
322
end if
323
end if ;(GEN_TREES_H) | !(STDC)
323
end if ;(GEN_TREES_H) | !(STDC)
324
	ret
324
	ret
325
endp
325
endp
326
 
326
 
327
; ===========================================================================
327
; ===========================================================================
328
; Genererate the file trees.h describing the static trees.
328
; Genererate the file trees.h describing the static trees.
329
 
329
 
330
;#  define SEPARATOR(i, last, width) \
330
;#  define SEPARATOR(i, last, width) \
331
;      ((i) == (last)? "\n};\n\n" :    \
331
;      ((i) == (last)? "\n};\n\n" :    \
332
;       ((i) % (width) == (width)-1 ? ",\n" : ", "))
332
;       ((i) % (width) == (width)-1 ? ",\n" : ", "))
333
 
333
 
334
;void ()
334
;void ()
335
align 4
335
align 4
336
proc gen_trees_header
336
proc gen_trees_header
337
;    FILE *header = fopen("trees.inc", "w");
337
;    FILE *header = fopen("trees.inc", "w");
338
;    int i;
338
;    int i;
339
 
339
 
340
;    Assert (header != NULL, "Can't open trees.inc");
340
;    Assert (header != NULL, "Can't open trees.inc");
341
;    fprintf(header,
341
;    fprintf(header,
342
;            "/* header created automatically with -DGEN_TREES_H */\n\n");
342
;            "/* header created automatically with -DGEN_TREES_H */\n\n");
343
 
343
 
344
;    fprintf(header, "local const ct_data static_ltree[L_CODES+2] = {\n");
344
;    fprintf(header, "local const ct_data static_ltree[L_CODES+2] = {\n");
345
;    for (i = 0; i < L_CODES+2; i++) {
345
;    for (i = 0; i < L_CODES+2; i++) {
346
;        fprintf(header, "{{%3u},{%3u}}%s", static_ltree[i].Code,
346
;        fprintf(header, "{{%3u},{%3u}}%s", static_ltree[i].Code,
347
;                static_ltree[i].Len, SEPARATOR(i, L_CODES+1, 5));
347
;                static_ltree[i].Len, SEPARATOR(i, L_CODES+1, 5));
348
;    }
348
;    }
349
 
349
 
350
;    fprintf(header, "local const ct_data static_dtree[D_CODES] = {\n");
350
;    fprintf(header, "local const ct_data static_dtree[D_CODES] = {\n");
351
;    for (i = 0; i < D_CODES; i++) {
351
;    for (i = 0; i < D_CODES; i++) {
352
;        fprintf(header, "{{%2u},{%2u}}%s", static_dtree[i].Code,
352
;        fprintf(header, "{{%2u},{%2u}}%s", static_dtree[i].Code,
353
;                static_dtree[i].Len, SEPARATOR(i, D_CODES-1, 5));
353
;                static_dtree[i].Len, SEPARATOR(i, D_CODES-1, 5));
354
;    }
354
;    }
355
 
355
 
356
;    fprintf(header, "const uch ZLIB_INTERNAL _dist_code[DIST_CODE_LEN] = {\n");
356
;    fprintf(header, "const uch ZLIB_INTERNAL _dist_code[DIST_CODE_LEN] = {\n");
357
;    for (i = 0; i < DIST_CODE_LEN; i++) {
357
;    for (i = 0; i < DIST_CODE_LEN; i++) {
358
;        fprintf(header, "%2u%s", _dist_code[i],
358
;        fprintf(header, "%2u%s", _dist_code[i],
359
;                SEPARATOR(i, DIST_CODE_LEN-1, 20));
359
;                SEPARATOR(i, DIST_CODE_LEN-1, 20));
360
;    }
360
;    }
361
 
361
 
362
;    fprintf(header,
362
;    fprintf(header,
363
;        "const uch ZLIB_INTERNAL _length_code[MAX_MATCH-MIN_MATCH+1]= {\n");
363
;        "const uch ZLIB_INTERNAL _length_code[MAX_MATCH-MIN_MATCH+1]= {\n");
364
;    for (i = 0; i < MAX_MATCH-MIN_MATCH+1; i++) {
364
;    for (i = 0; i < MAX_MATCH-MIN_MATCH+1; i++) {
365
;        fprintf(header, "%2u%s", _length_code[i],
365
;        fprintf(header, "%2u%s", _length_code[i],
366
;                SEPARATOR(i, MAX_MATCH-MIN_MATCH, 20));
366
;                SEPARATOR(i, MAX_MATCH-MIN_MATCH, 20));
367
;    }
367
;    }
368
 
368
 
369
;    fprintf(header, "local const int base_length[LENGTH_CODES] = {\n");
369
;    fprintf(header, "local const int base_length[LENGTH_CODES] = {\n");
370
;    for (i = 0; i < LENGTH_CODES; i++) {
370
;    for (i = 0; i < LENGTH_CODES; i++) {
371
;        fprintf(header, "%1u%s", base_length[i],
371
;        fprintf(header, "%1u%s", base_length[i],
372
;                SEPARATOR(i, LENGTH_CODES-1, 20));
372
;                SEPARATOR(i, LENGTH_CODES-1, 20));
373
;    }
373
;    }
374
 
374
 
375
;    fprintf(header, "local const int base_dist[D_CODES] = {\n");
375
;    fprintf(header, "local const int base_dist[D_CODES] = {\n");
376
;    for (i = 0; i < D_CODES; i++) {
376
;    for (i = 0; i < D_CODES; i++) {
377
;        fprintf(header, "%5u%s", base_dist[i],
377
;        fprintf(header, "%5u%s", base_dist[i],
378
;                SEPARATOR(i, D_CODES-1, 10));
378
;                SEPARATOR(i, D_CODES-1, 10));
379
;    }
379
;    }
380
 
380
 
381
;    fclose(header);
381
;    fclose(header);
382
	ret
382
	ret
383
endp
383
endp
384
 
384
 
385
; ===========================================================================
385
; ===========================================================================
386
; Initialize the tree data structures for a new zlib stream.
386
; Initialize the tree data structures for a new zlib stream.
387
 
387
 
388
;void (s)
388
;void (s)
389
;    deflate_state* s
389
;    deflate_state* s
390
align 4
390
align 4
391
proc _tr_init uses eax edi, s:dword
391
proc _tr_init uses eax edi, s:dword
392
	mov edi,[s]
392
	mov edi,[s]
393
	zlib_debug '_tr_init'
393
	zlib_debug '_tr_init'
394
	call tr_static_init
394
	call tr_static_init
395
 
395
 
396
	mov eax,edi
396
	mov eax,edi
397
	add eax,deflate_state.dyn_ltree
397
	add eax,deflate_state.dyn_ltree
398
	mov [edi+deflate_state.l_desc.dyn_tree],eax
398
	mov [edi+deflate_state.l_desc.dyn_tree],eax
399
	mov [edi+deflate_state.l_desc.stat_desc],static_l_desc
399
	mov [edi+deflate_state.l_desc.stat_desc],static_l_desc
400
 
400
 
401
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
401
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
402
	mov [edi+deflate_state.d_desc.dyn_tree],eax
402
	mov [edi+deflate_state.d_desc.dyn_tree],eax
403
	mov [edi+deflate_state.d_desc.stat_desc],static_d_desc
403
	mov [edi+deflate_state.d_desc.stat_desc],static_d_desc
404
 
404
 
405
	add eax,deflate_state.bl_tree-deflate_state.dyn_dtree
405
	add eax,deflate_state.bl_tree-deflate_state.dyn_dtree
406
	mov [edi+deflate_state.bl_desc.dyn_tree],eax
406
	mov [edi+deflate_state.bl_desc.dyn_tree],eax
407
	mov [edi+deflate_state.bl_desc.stat_desc],static_bl_desc;
407
	mov [edi+deflate_state.bl_desc.stat_desc],static_bl_desc;
408
 
408
 
409
	mov word[edi+deflate_state.bi_buf],0
409
	mov word[edi+deflate_state.bi_buf],0
410
	mov dword[edi+deflate_state.bi_valid],0
410
	mov dword[edi+deflate_state.bi_valid],0
411
if DEBUG eq 1
411
if DEBUG eq 1
412
	mov dword[edi+deflate_state.compressed_len],0
412
	mov dword[edi+deflate_state.compressed_len],0
413
	mov dword[edi+deflate_state.bits_sent],0
413
	mov dword[edi+deflate_state.bits_sent],0
414
end if
414
end if
415
 
415
 
416
	; Initialize the first block of the first file:
416
	; Initialize the first block of the first file:
417
	stdcall init_block,edi
417
	stdcall init_block,edi
418
	ret
418
	ret
419
endp
419
endp
420
 
420
 
421
; ===========================================================================
421
; ===========================================================================
422
; Initialize a new block.
422
; Initialize a new block.
423
 
423
 
424
;void (s)
424
;void (s)
425
;    deflate_state* s
425
;    deflate_state* s
426
align 4
426
align 4
427
proc init_block uses eax ecx edi, s:dword
427
proc init_block uses eax ecx edi, s:dword
428
	mov edi,[s]
428
	mov edi,[s]
429
 
429
 
430
	; Initialize the trees.
430
	; Initialize the trees.
431
	mov eax,edi
431
	mov eax,edi
432
	add eax,deflate_state.dyn_ltree+Freq
432
	add eax,deflate_state.dyn_ltree+Freq
433
	mov ecx,L_CODES
433
	mov ecx,L_CODES
434
	@@:
434
	@@:
435
		mov word[eax],0
435
		mov word[eax],0
436
		add eax,sizeof.ct_data
436
		add eax,sizeof.ct_data
437
		loop @b
437
		loop @b
438
	mov eax,edi
438
	mov eax,edi
439
	add eax,deflate_state.dyn_dtree+Freq
439
	add eax,deflate_state.dyn_dtree+Freq
440
	mov ecx,D_CODES
440
	mov ecx,D_CODES
441
	@@:
441
	@@:
442
		mov word[eax],0
442
		mov word[eax],0
443
		add eax,sizeof.ct_data
443
		add eax,sizeof.ct_data
444
		loop @b
444
		loop @b
445
	mov eax,edi
445
	mov eax,edi
446
	add eax,deflate_state.bl_tree+Freq
446
	add eax,deflate_state.bl_tree+Freq
447
	mov ecx,BL_CODES
447
	mov ecx,BL_CODES
448
	@@:
448
	@@:
449
		mov word[eax],0
449
		mov word[eax],0
450
		add eax,sizeof.ct_data
450
		add eax,sizeof.ct_data
451
		loop @b
451
		loop @b
452
 
452
 
453
	mov word[edi+sizeof.ct_data*END_BLOCK+deflate_state.dyn_ltree+Freq],1
453
	mov word[edi+sizeof.ct_data*END_BLOCK+deflate_state.dyn_ltree+Freq],1
454
	mov dword[edi+deflate_state.static_len],0
454
	mov dword[edi+deflate_state.static_len],0
455
	mov dword[edi+deflate_state.opt_len],0
455
	mov dword[edi+deflate_state.opt_len],0
456
	mov dword[edi+deflate_state.matches],0
456
	mov dword[edi+deflate_state.matches],0
457
	mov dword[edi+deflate_state.last_lit],0
457
	mov dword[edi+deflate_state.last_lit],0
458
	ret
458
	ret
459
endp
459
endp
460
 
460
 
461
SMALLEST equ 1
461
SMALLEST equ 1
462
; Index within the heap array of least frequent node in the Huffman tree
462
; Index within the heap array of least frequent node in the Huffman tree
463
 
463
 
464
 
464
 
465
; ===========================================================================
465
; ===========================================================================
466
; Remove the smallest element from the heap and recreate the heap with
466
; Remove the smallest element from the heap and recreate the heap with
467
; one less element. Updates heap and heap_len.
467
; one less element. Updates heap and heap_len.
468
 
468
 
469
macro pqremove s, tree, top
469
macro pqremove s, tree, top
470
{
470
{
471
	mov eax,s
471
	mov eax,s
472
	add eax,deflate_state.heap+2*SMALLEST
472
	add eax,deflate_state.heap+2*SMALLEST
473
	movzx top,word[eax]
473
	movzx top,word[eax]
474
push ebx
474
push ebx
475
	mov ebx,[s+deflate_state.heap_len]
475
	mov ebx,[s+deflate_state.heap_len]
476
	mov bx,[s+deflate_state.heap+2*ebx]
476
	mov bx,[s+deflate_state.heap+2*ebx]
477
	mov word[eax],bx
477
	mov word[eax],bx
478
	dec dword[s+deflate_state.heap_len]
478
	dec dword[s+deflate_state.heap_len]
479
pop ebx
479
pop ebx
480
	stdcall pqdownheap, s, tree, SMALLEST
480
	stdcall pqdownheap, s, tree, SMALLEST
481
}
481
}
482
 
482
 
483
; ===========================================================================
483
; ===========================================================================
484
; Compares to subtrees, using the tree depth as tie breaker when
484
; Compares to subtrees, using the tree depth as tie breaker when
485
; the subtrees have equal frequency. This minimizes the worst case length.
485
; the subtrees have equal frequency. This minimizes the worst case length.
486
 
486
 
487
macro smaller tree, n, m, depth, m_end
487
macro smaller tree, n, m, depth, m_end
488
{
488
{
489
;if (..<.. || (..==.. && depth[n] <= depth[m]))
489
;if (..<.. || (..==.. && depth[n] <= depth[m]))
490
local .end0
490
local .end0
491
	movzx eax,n
491
	movzx eax,n
492
	imul eax,sizeof.ct_data
492
	imul eax,sizeof.ct_data
493
	add eax,tree
493
	add eax,tree
494
	mov ax,word[eax+Freq]
494
	mov ax,word[eax+Freq]
495
	movzx ebx,m
495
	movzx ebx,m
496
	imul ebx,sizeof.ct_data
496
	imul ebx,sizeof.ct_data
497
	add ebx,tree
497
	add ebx,tree
498
	mov bx,word[ebx+Freq]
498
	mov bx,word[ebx+Freq]
499
	cmp ax,bx
499
	cmp ax,bx
500
	jl .end0
500
	jl .end0
501
	jne m_end
501
	jne m_end
502
	movzx eax,n
502
	movzx eax,n
503
	add eax,depth
503
	add eax,depth
504
	mov al,byte[eax]
504
	mov al,byte[eax]
505
	movzx ebx,m
505
	movzx ebx,m
506
	add ebx,depth
506
	add ebx,depth
507
	mov bl,byte[ebx]
507
	mov bl,byte[ebx]
508
	cmp al,bl
508
	cmp al,bl
509
	jg m_end
509
	jg m_end
510
	.end0:
510
	.end0:
511
}
511
}
512
 
512
 
513
; ===========================================================================
513
; ===========================================================================
514
; Restore the heap property by moving down the tree starting at node k,
514
; Restore the heap property by moving down the tree starting at node k,
515
; exchanging a node with the smallest of its two sons if necessary, stopping
515
; exchanging a node with the smallest of its two sons if necessary, stopping
516
; when the heap property is re-established (each father smaller than its
516
; when the heap property is re-established (each father smaller than its
517
; two sons).
517
; two sons).
518
 
518
 
519
;void (s, tree, k)
519
;void (s, tree, k)
520
;    deflate_state* s
520
;    deflate_state* s
521
;    ct_data* tree ;the tree to restore
521
;    ct_data* tree ;the tree to restore
522
;    int      k    ;node to move down
522
;    int      k    ;node to move down
523
align 4
523
align 4
524
proc pqdownheap, s:dword, tree:dword, k:dword
524
proc pqdownheap, s:dword, tree:dword, k:dword
525
locals
525
locals
526
	v dw ?
526
	v dw ?
527
endl
527
endl
528
pushad
528
pushad
529
	mov edi,[s]
529
	mov edi,[s]
530
	mov eax,[k]
530
	mov eax,[k]
531
	zlib_debug 'pqdownheap k = %d',eax
531
	zlib_debug 'pqdownheap k = %d',eax
532
	mov esi,eax
532
	mov esi,eax
533
	shl esi,1
533
	shl esi,1
534
	mov ax,[edi+deflate_state.heap+2*eax]
534
	mov ax,[edi+deflate_state.heap+2*eax]
535
	mov [v],ax
535
	mov [v],ax
536
	;esi = j ;left son of k
536
	;esi = j ;left son of k
537
	.cycle0: ;while (..<=..)
537
	.cycle0: ;while (..<=..)
538
		cmp esi,[edi+deflate_state.heap_len]
538
		cmp esi,[edi+deflate_state.heap_len]
539
		jg .cycle0end
539
		jg .cycle0end
540
		; Set j to the smallest of the two sons:
540
		; Set j to the smallest of the two sons:
541
		;;cmp esi,[edi+deflate_state.heap_len]
541
		;;cmp esi,[edi+deflate_state.heap_len]
542
		jge .end1 ;if (..<.. &&
542
		jge .end1 ;if (..<.. &&
543
		mov ecx,edi
543
		mov ecx,edi
544
		add ecx,deflate_state.depth
544
		add ecx,deflate_state.depth
545
		mov edx,esi
545
		mov edx,esi
546
		shl edx,1
546
		shl edx,1
547
		add edx,edi
547
		add edx,edi
548
		add edx,deflate_state.heap
548
		add edx,deflate_state.heap
549
		smaller [tree], word[edx+2], word[edx], ecx, .end1
549
		smaller [tree], word[edx+2], word[edx], ecx, .end1
550
			inc esi
550
			inc esi
551
		.end1:
551
		.end1:
552
		; Exit if v is smaller than both sons
552
		; Exit if v is smaller than both sons
553
		mov ecx,edi
553
		mov ecx,edi
554
		add ecx,deflate_state.depth
554
		add ecx,deflate_state.depth
555
		mov dx,[edi+deflate_state.heap+2*esi]
555
		mov dx,[edi+deflate_state.heap+2*esi]
556
		smaller [tree], [v], dx, ecx, .end2
556
		smaller [tree], [v], dx, ecx, .end2
557
			jmp .cycle0end ;break
557
			jmp .cycle0end ;break
558
		.end2:
558
		.end2:
559
		; Exchange v with the smallest son
559
		; Exchange v with the smallest son
560
		mov dx,[edi+deflate_state.heap+2*esi]
560
		mov dx,[edi+deflate_state.heap+2*esi]
561
		mov eax,[k]
561
		mov eax,[k]
562
		mov [edi+deflate_state.heap+2*eax],dx
562
		mov [edi+deflate_state.heap+2*eax],dx
563
		mov [k],esi
563
		mov [k],esi
564
		; And continue down the tree, setting j to the left son of k
564
		; And continue down the tree, setting j to the left son of k
565
		shl esi,1
565
		shl esi,1
566
		jmp .cycle0
566
		jmp .cycle0
567
	.cycle0end:
567
	.cycle0end:
568
	mov eax,[k]
568
	mov eax,[k]
569
	mov bx,[v]
569
	mov bx,[v]
570
	mov [edi+deflate_state.heap+2*eax],bx
570
	mov [edi+deflate_state.heap+2*eax],bx
571
popad
571
popad
572
	ret
572
	ret
573
endp
573
endp
574
 
574
 
575
; ===========================================================================
575
; ===========================================================================
576
; Compute the optimal bit lengths for a tree and update the total bit length
576
; Compute the optimal bit lengths for a tree and update the total bit length
577
; for the current block.
577
; for the current block.
578
; IN assertion: the fields freq and dad are set, heap[heap_max] and
578
; IN assertion: the fields freq and dad are set, heap[heap_max] and
579
;    above are the tree nodes sorted by increasing frequency.
579
;    above are the tree nodes sorted by increasing frequency.
580
; OUT assertions: the field len is set to the optimal bit length, the
580
; OUT assertions: the field len is set to the optimal bit length, the
581
;     array bl_count contains the frequencies for each bit length.
581
;     array bl_count contains the frequencies for each bit length.
582
;     The length opt_len is updated; static_len is also updated if stree is
582
;     The length opt_len is updated; static_len is also updated if stree is
583
;     not null.
583
;     not null.
584
 
584
 
585
;void (s, desc)
585
;void (s, desc)
586
;    deflate_state* s
586
;    deflate_state* s
587
;    tree_desc* desc ;the tree descriptor
587
;    tree_desc* desc ;the tree descriptor
588
align 4
588
align 4
589
proc gen_bitlen, s:dword, desc:dword
589
proc gen_bitlen, s:dword, desc:dword
590
locals
590
locals
591
	tree  dd ? ;ct_data* ;= desc.dyn_tree
591
	tree  dd ? ;ct_data* ;= desc.dyn_tree
592
	max_code dd ? ;int   ;= desc.max_code
592
	max_code dd ? ;int   ;= desc.max_code
593
	stree dd ? ;ct_data* ;= desc.stat_desc.static_tree
593
	stree dd ? ;ct_data* ;= desc.stat_desc.static_tree
594
	extra dd ? ;intf*    ;= desc.stat_desc.extra_bits
594
	extra dd ? ;intf*    ;= desc.stat_desc.extra_bits
595
	base  dd ? ;int      ;= desc.stat_desc.extra_base
595
	base  dd ? ;int      ;= desc.stat_desc.extra_base
596
	max_length dd ? ;int ;= desc.stat_desc.max_length
596
	max_length dd ? ;int ;= desc.stat_desc.max_length
597
	h     dd ? ;int ;heap index
597
	h     dd ? ;int ;heap index
598
	m     dd ? ;int ;iterate over the tree elements
598
	m     dd ? ;int ;iterate over the tree elements
599
	bits  dd ? ;int ;bit length
599
	bits  dd ? ;int ;bit length
600
	xbits dd ? ;int ;extra bits
600
	xbits dd ? ;int ;extra bits
601
	f     dw ? ;uint_16 ;frequency
601
	f     dw ? ;uint_16 ;frequency
602
	overflow dd 0 ;int ;number of elements with bit length too large
602
	overflow dd 0 ;int ;number of elements with bit length too large
603
endl
603
endl
604
pushad
604
pushad
605
	zlib_debug 'gen_bitlen'
605
	zlib_debug 'gen_bitlen'
606
	mov edi,[s]
606
	mov edi,[s]
607
	mov edx,[desc]
607
	mov edx,[desc]
608
	mov eax,[edx+tree_desc.dyn_tree]
608
	mov eax,[edx+tree_desc.dyn_tree]
609
	mov [tree],eax
609
	mov [tree],eax
610
	mov eax,[edx+tree_desc.max_code]
610
	mov eax,[edx+tree_desc.max_code]
611
	mov [max_code],eax
611
	mov [max_code],eax
612
	mov ebx,[edx+tree_desc.stat_desc]
612
	mov ebx,[edx+tree_desc.stat_desc]
613
	mov eax,[ebx+static_tree_desc.static_tree]
613
	mov eax,[ebx+static_tree_desc.static_tree]
614
	mov [stree],eax
614
	mov [stree],eax
615
	mov eax,[ebx+static_tree_desc.extra_bits]
615
	mov eax,[ebx+static_tree_desc.extra_bits]
616
	mov [extra],eax
616
	mov [extra],eax
617
	mov eax,[ebx+static_tree_desc.extra_base]
617
	mov eax,[ebx+static_tree_desc.extra_base]
618
	mov [base],eax
618
	mov [base],eax
619
	mov eax,[ebx+static_tree_desc.max_length]
619
	mov eax,[ebx+static_tree_desc.max_length]
620
	mov [max_length],eax
620
	mov [max_length],eax
621
 
621
 
622
	xor ecx,ecx
622
	xor ecx,ecx
623
	.cycle0:
623
	.cycle0:
624
	cmp ecx,MAX_BITS
624
	cmp ecx,MAX_BITS
625
	jg .cycle0end ;for (..;..<=..;..)
625
	jg .cycle0end ;for (..;..<=..;..)
626
		mov word[edi+deflate_state.bl_count+2*ecx],0
626
		mov word[edi+deflate_state.bl_count+2*ecx],0
627
		inc ecx
627
		inc ecx
628
		jmp .cycle0
628
		jmp .cycle0
629
align 4
629
align 4
630
	.cycle0end:
630
	.cycle0end:
631
 
631
 
632
	; In a first pass, compute the optimal bit lengths (which may
632
	; In a first pass, compute the optimal bit lengths (which may
633
	; overflow in the case of the bit length tree).
633
	; overflow in the case of the bit length tree).
634
 
634
 
635
	mov eax,[edi+deflate_state.heap_max]
635
	mov eax,[edi+deflate_state.heap_max]
636
	movzx eax,word[edi+deflate_state.heap+2*eax]
636
	movzx eax,word[edi+deflate_state.heap+2*eax]
637
	imul eax,sizeof.ct_data
637
	imul eax,sizeof.ct_data
638
	add eax,[tree]
638
	add eax,[tree]
639
	mov word[eax+Len],0 ;root of the heap
639
	mov word[eax+Len],0 ;root of the heap
640
 
640
 
641
	mov eax,[edi+deflate_state.heap_max]
641
	mov eax,[edi+deflate_state.heap_max]
642
	inc eax
642
	inc eax
643
	mov [h],eax
643
	mov [h],eax
644
	.cycle1:
644
	.cycle1:
645
	cmp dword[h],HEAP_SIZE
645
	cmp dword[h],HEAP_SIZE
646
	jge .cycle1end ;for (..;..<..;..)
646
	jge .cycle1end ;for (..;..<..;..)
647
		mov eax,[h]
647
		mov eax,[h]
648
		movzx ecx,word[edi+deflate_state.heap+2*eax]
648
		movzx ecx,word[edi+deflate_state.heap+2*eax]
649
		;ecx = n
649
		;ecx = n
650
		mov eax,sizeof.ct_data
650
		mov eax,sizeof.ct_data
651
		imul eax,ecx
651
		imul eax,ecx
652
		add eax,[tree]
652
		add eax,[tree]
653
		movzx eax,word[eax+Dad]
653
		movzx eax,word[eax+Dad]
654
		imul eax,sizeof.ct_data
654
		imul eax,sizeof.ct_data
655
		add eax,[tree]
655
		add eax,[tree]
656
		movzx eax,word[eax+Len]
656
		movzx eax,word[eax+Len]
657
		inc eax
657
		inc eax
658
		mov [bits],eax ;bits = tree[tree[n].Dad].Len + 1
658
		mov [bits],eax ;bits = tree[tree[n].Dad].Len + 1
659
		mov eax,[max_length]
659
		mov eax,[max_length]
660
		cmp [bits],eax
660
		cmp [bits],eax
661
		jle @f ;if (..>..)
661
		jle @f ;if (..>..)
662
			mov [bits],eax
662
			mov [bits],eax
663
			inc dword[overflow]
663
			inc dword[overflow]
664
		@@:
664
		@@:
665
		mov esi,[bits]
665
		mov esi,[bits]
666
		mov eax,sizeof.ct_data
666
		mov eax,sizeof.ct_data
667
		imul eax,ecx
667
		imul eax,ecx
668
		add eax,[tree]
668
		add eax,[tree]
669
		mov word[eax+Len],si
669
		mov word[eax+Len],si
670
		; We overwrite tree[n].Dad which is no longer needed
670
		; We overwrite tree[n].Dad which is no longer needed
671
 
671
 
672
		cmp ecx,[max_code]
672
		cmp ecx,[max_code]
673
		jle @f
673
		jle @f
674
			inc dword[h]
674
			inc dword[h]
675
			jmp .cycle1 ;if (..>..) continue ;not a leaf node
675
			jmp .cycle1 ;if (..>..) continue ;not a leaf node
676
		@@:
676
		@@:
677
 
677
 
678
		mov eax,[bits]
678
		mov eax,[bits]
679
		shl eax,1 ;*= sizeof.uint_16
679
		shl eax,1 ;*= sizeof.uint_16
680
		inc word[eax+edi+deflate_state.bl_count]
680
		inc word[eax+edi+deflate_state.bl_count]
681
		mov dword[xbits],0
681
		mov dword[xbits],0
682
		cmp ecx,[base]
682
		cmp ecx,[base]
683
		jl @f ;if (..>=..)
683
		jl @f ;if (..>=..)
684
			mov eax,ecx
684
			mov eax,ecx
685
			sub eax,[base]
685
			sub eax,[base]
686
			shl eax,2 ;*= sizeof.dd
686
			shl eax,2 ;*= sizeof.dd
687
			add eax,[extra]
687
			add eax,[extra]
688
			mov eax,[eax]
688
			mov eax,[eax]
689
			mov [xbits],eax
689
			mov [xbits],eax
690
		@@:
690
		@@:
691
		mov eax,sizeof.ct_data
691
		mov eax,sizeof.ct_data
692
		imul eax,ecx
692
		imul eax,ecx
693
		add eax,[tree]
693
		add eax,[tree]
694
		movzx eax,word[eax+Freq]
694
		movzx eax,word[eax+Freq]
695
		mov [f],ax
695
		mov [f],ax
696
		mov esi,[bits]
696
		mov esi,[bits]
697
		add esi,[xbits]
697
		add esi,[xbits]
698
		imul eax,esi
698
		imul eax,esi
699
		add [edi+deflate_state.opt_len],eax
699
		add [edi+deflate_state.opt_len],eax
700
		cmp dword[stree],0
700
		cmp dword[stree],0
701
		je @f ;if (..)
701
		je @f ;if (..)
702
			movzx eax,word[f]
702
			movzx eax,word[f]
703
			mov esi,sizeof.ct_data
703
			mov esi,sizeof.ct_data
704
			imul esi,ecx
704
			imul esi,ecx
705
			add esi,[tree]
705
			add esi,[tree]
706
			movzx esi,word[esi+Len]
706
			movzx esi,word[esi+Len]
707
			add esi,[xbits]
707
			add esi,[xbits]
708
			imul eax,esi
708
			imul eax,esi
709
			add [edi+deflate_state.static_len],eax
709
			add [edi+deflate_state.static_len],eax
710
		@@:
710
		@@:
711
		inc dword[h]
711
		inc dword[h]
712
		jmp .cycle1
712
		jmp .cycle1
713
align 4
713
align 4
714
	.cycle1end:
714
	.cycle1end:
715
	cmp dword[overflow],0
715
	cmp dword[overflow],0
716
	je .end_f ;if (..==0) return
716
	je .end_f ;if (..==0) return
717
 
717
 
718
;    Trace((stderr,"\nbit length overflow\n"));
718
;    Trace((stderr,"\nbit length overflow\n"));
719
	; This happens for example on obj2 and pic of the Calgary corpus
719
	; This happens for example on obj2 and pic of the Calgary corpus
720
 
720
 
721
	; Find the first bit length which could increase:
721
	; Find the first bit length which could increase:
722
	.cycle2: ;do
722
	.cycle2: ;do
723
		mov eax,[max_length]
723
		mov eax,[max_length]
724
		dec eax
724
		dec eax
725
		mov [bits],eax
725
		mov [bits],eax
726
		shl eax,1 ;*= sizeof.dw
726
		shl eax,1 ;*= sizeof.dw
727
		add eax,edi
727
		add eax,edi
728
		add eax,deflate_state.bl_count
728
		add eax,deflate_state.bl_count
729
		@@:
729
		@@:
730
		cmp word[eax],0
730
		cmp word[eax],0
731
		jne @f ;while (..==0) bits--
731
		jne @f ;while (..==0) bits--
732
			dec dword[bits]
732
			dec dword[bits]
733
			sub eax,2
733
			sub eax,2
734
			jmp @b
734
			jmp @b
-
 
735
align 4
735
		@@:
736
		@@:
736
		dec word[eax]     ;move one leaf down the tree
737
		dec word[eax]     ;move one leaf down the tree
737
		add word[eax+2],2 ;move one overflow item as its brother
738
		add word[eax+2],2 ;move one overflow item as its brother
738
		mov eax,[max_length]
739
		mov eax,[max_length]
739
		dec word[edi+deflate_state.bl_count+2*eax]
740
		dec word[edi+deflate_state.bl_count+2*eax]
740
		; The brother of the overflow item also moves one step up,
741
		; The brother of the overflow item also moves one step up,
741
		; but this does not affect bl_count[max_length]
742
		; but this does not affect bl_count[max_length]
742
 
743
 
743
		sub dword[overflow],2
744
		sub dword[overflow],2
744
		cmp dword[overflow],0
745
		cmp dword[overflow],0
745
		jg .cycle2 ;while (..>0)
746
		jg .cycle2 ;while (..>0)
746
 
747
 
747
	; Now recompute all bit lengths, scanning in increasing frequency.
748
	; Now recompute all bit lengths, scanning in increasing frequency.
748
	; h is still equal to HEAP_SIZE. (It is simpler to reconstruct all
749
	; h is still equal to HEAP_SIZE. (It is simpler to reconstruct all
749
	; lengths instead of fixing only the wrong ones. This idea is taken
750
	; lengths instead of fixing only the wrong ones. This idea is taken
750
	; from 'ar' written by Haruhiko Okumura.)
751
	; from 'ar' written by Haruhiko Okumura.)
751
 
752
 
752
	mov eax,[max_length]
753
	mov eax,[max_length]
753
	mov [bits],eax
754
	mov [bits],eax
754
	.cycle3:
755
	.cycle3:
755
	cmp dword[bits],0
756
	cmp dword[bits],0
756
	je .end_f ;for (..;..!=0;..)
757
	je .end_f ;for (..;..!=0;..)
757
		mov eax,[bits]
758
		mov eax,[bits]
758
		shl eax,1 ;*= sizeof.dw
759
		shl eax,1 ;*= sizeof.dw
759
		movzx ecx,word[eax+edi+deflate_state.bl_count]
760
		movzx ecx,word[eax+edi+deflate_state.bl_count]
760
		.cycle4: ;while (..!=0)
761
		.cycle4: ;while (..!=0)
761
		cmp ecx,0
762
		cmp ecx,0
762
		je .cycle4end
763
		je .cycle4end
763
			dec dword[h]
764
			dec dword[h]
764
			mov eax,[h]
765
			mov eax,[h]
765
			movzx eax,word[edi+deflate_state.heap+2*eax]
766
			movzx eax,word[edi+deflate_state.heap+2*eax]
766
			mov [m],eax ;m = s.heap[--h]
767
			mov [m],eax ;m = s.heap[--h]
767
			cmp eax,[max_code]
768
			cmp eax,[max_code]
768
			jle @f ;if (..>..) continue
769
			jg .cycle4 ;if (..>..) continue
769
				dec ecx
-
 
770
				jmp .cycle4			
-
 
771
			@@:
-
 
772
			mov esi,[m]
770
			mov esi,[m]
773
			imul esi,sizeof.ct_data
771
			imul esi,sizeof.ct_data
774
			add esi,[tree] ;esi = &tree[m]
772
			add esi,[tree] ;esi = &tree[m]
775
			mov eax,[bits]
773
			mov eax,[bits]
776
			cmp word[esi+Len],ax
774
			cmp word[esi+Len],ax
777
			je @f ;if (..!=..)
775
			je @f ;if (..!=..)
778
;                Trace((stderr,"code %d bits %d->%d\n", m, tree[m].Len, bits));
776
;                Trace((stderr,"code %d bits %d->%d\n", m, tree[m].Len, bits));
779
				movzx ebx,word[esi+Len]
777
				movzx ebx,word[esi+Len]
780
				sub eax,ebx
778
				sub eax,ebx
781
				movzx ebx,word[esi+Freq]
779
				movzx ebx,word[esi+Freq]
782
				imul eax,ebx ;eax = (bits - tree[m].Len) * tree[m].Freq
780
				imul eax,ebx ;eax = (bits - tree[m].Len) * tree[m].Freq
783
				add [edi+deflate_state.opt_len],eax
781
				add [edi+deflate_state.opt_len],eax
784
				mov eax,[bits]
782
				mov eax,[bits]
785
				mov word[esi+Len],ax
783
				mov word[esi+Len],ax
786
			@@:
784
			@@:
787
			dec ecx
785
			dec ecx
788
			jmp .cycle4
786
			jmp .cycle4
-
 
787
align 4
789
		.cycle4end:
788
		.cycle4end:
790
		dec dword[bits]
789
		dec dword[bits]
791
		jmp .cycle3
790
		jmp .cycle3
-
 
791
align 4
792
.end_f:
792
.end_f:
793
popad
793
popad
794
	ret
794
	ret
795
endp
795
endp
796
 
796
 
797
; ===========================================================================
797
; ===========================================================================
798
; Generate the codes for a given tree and bit counts (which need not be
798
; Generate the codes for a given tree and bit counts (which need not be
799
; optimal).
799
; optimal).
800
; IN assertion: the array bl_count contains the bit length statistics for
800
; IN assertion: the array bl_count contains the bit length statistics for
801
; the given tree and the field len is set for all tree elements.
801
; the given tree and the field len is set for all tree elements.
802
; OUT assertion: the field code is set for all tree elements of non
802
; OUT assertion: the field code is set for all tree elements of non
803
;     zero code length.
803
;     zero code length.
804
 
804
 
805
;void (tree, max_code, bl_count)
805
;void (tree, max_code, bl_count)
806
;    ct_data *tree     ;the tree to decorate
806
;    ct_data *tree     ;the tree to decorate
807
;    int max_code      ;largest code with non zero frequency
807
;    int max_code      ;largest code with non zero frequency
808
;    uint_16p bl_count ;number of codes at each bit length
808
;    uint_16p bl_count ;number of codes at each bit length
809
align 4
809
align 4
810
proc gen_codes uses eax ebx ecx edx edi, tree:dword, max_code:dword, bl_count:dword
810
proc gen_codes uses eax ebx ecx edx edi, tree:dword, max_code:dword, bl_count:dword
811
locals
811
locals
812
	u_code dw 0 ;uint_16 ;running code value
812
	u_code dw 0 ;uint_16 ;running code value
813
	bits   dd 1 ;int ;bit index
813
	bits   dd 1 ;int ;bit index
814
	next_code rw MAX_BITS+1 ;uint_16[] ;next code value for each bit length
814
	next_code rw MAX_BITS+1 ;uint_16[] ;next code value for each bit length
815
endl
815
endl
816
	; The distribution counts are first used to generate the code values
816
	; The distribution counts are first used to generate the code values
817
	; without bit reversal.
817
	; without bit reversal.
818
	zlib_debug 'gen_codes'
818
	zlib_debug 'gen_codes'
819
	mov ebx,ebp
819
	mov ebx,ebp
820
	sub ebx,2*(MAX_BITS+1)
820
	sub ebx,2*(MAX_BITS+1)
821
 
821
 
822
	.cycle0: ;for (..;..<=..;..)
822
	.cycle0: ;for (..;..<=..;..)
823
	cmp dword[bits],MAX_BITS
823
	cmp dword[bits],MAX_BITS
824
	jg .cycle0end
824
	jg .cycle0end
825
		mov eax,[bits]
825
		mov eax,[bits]
826
		dec eax
826
		dec eax
827
		shl eax,1
827
		shl eax,1
828
		add eax,[bl_count]
828
		add eax,[bl_count]
829
		mov ax,word[eax]
829
		mov ax,word[eax]
830
		add ax,[u_code]
830
		add ax,[u_code]
831
		shl ax,1 ;ax = (u_code + bl_count[bits-1]) << 1
831
		shl ax,1 ;ax = (u_code + bl_count[bits-1]) << 1
832
		mov [u_code],ax
832
		mov [u_code],ax
833
		mov ecx,[bits]
833
		mov ecx,[bits]
834
		mov word[ebx+2*ecx],ax ;next_code[bits] = u_code
834
		mov word[ebx+2*ecx],ax ;next_code[bits] = u_code
835
		inc dword[bits]
835
		inc dword[bits]
836
		jmp .cycle0
836
		jmp .cycle0
837
	.cycle0end:
837
	.cycle0end:
838
	; Check that the bit counts in bl_count are consistent. The last code
838
	; Check that the bit counts in bl_count are consistent. The last code
839
	; must be all ones.
839
	; must be all ones.
840
 
840
 
841
	mov eax,[bl_count]
841
	mov eax,[bl_count]
842
	mov ax,word[eax+2*MAX_BITS]
842
	mov ax,word[eax+2*MAX_BITS]
843
	add ax,[u_code]
843
	add ax,[u_code]
844
	dec ax
844
	dec ax
845
	cmp ax,(1 shl MAX_BITS)-1
845
	cmp ax,(1 shl MAX_BITS)-1
846
	je @f
846
	je @f
847
		zlib_assert 'inconsistent bit counts' ;Assert(..==..)
847
		zlib_assert 'inconsistent bit counts' ;Assert(..==..)
848
	@@:
848
	@@:
849
;    Tracev((stderr,"\ngen_codes: max_code %d ", max_code));
849
;    Tracev((stderr,"\ngen_codes: max_code %d ", max_code));
850
 
850
 
851
	xor ecx,ecx ;n = 0
851
	xor ecx,ecx ;n = 0
852
	.cycle1: ;for (..;..<=..;..)
852
	.cycle1: ;for (..;..<=..;..)
853
	cmp ecx,[max_code]
853
	cmp ecx,[max_code]
854
	jg .cycle1end
854
	jg .cycle1end
855
		mov edx,sizeof.ct_data
855
		mov edx,sizeof.ct_data
856
		imul edx,ecx
856
		imul edx,ecx
857
		add edx,[tree] ;edx = &tree[n]
857
		add edx,[tree] ;edx = &tree[n]
858
		movzx edi,word[edx+Len]
858
		movzx edi,word[edx+Len]
859
		cmp edi,0
859
		cmp edi,0
860
		jne @f ;if (..==0) continue
860
		jne @f ;if (..==0) continue
861
			inc ecx
861
			inc ecx
862
			jmp .cycle1
862
			jmp .cycle1
863
		@@:
863
		@@:
864
		; Now reverse the bits
864
		; Now reverse the bits
865
		movzx eax,word[ebx+2*edi]
865
		movzx eax,word[ebx+2*edi]
866
		stdcall bi_reverse, eax, edi
866
		stdcall bi_reverse, eax, edi
867
		mov word[edx+Code],ax
867
		mov word[edx+Code],ax
868
		inc word[ebx+2*edi]
868
		inc word[ebx+2*edi]
869
 
869
 
870
;        Tracecv(tree != static_ltree, (stderr,"\nn %3d %c l %2d c %4x (%x) ",
870
;        Tracecv(tree != static_ltree, (stderr,"\nn %3d %c l %2d c %4x (%x) ",
871
;             n, (isgraph(n) ? n : ' '), len, tree[n].Code, next_code[len]-1));
871
;             n, (isgraph(n) ? n : ' '), len, tree[n].Code, next_code[len]-1));
872
		inc ecx
872
		inc ecx
873
		jmp .cycle1
873
		jmp .cycle1
874
	.cycle1end:
874
	.cycle1end:
875
	ret
875
	ret
876
endp
876
endp
877
 
877
 
878
; ===========================================================================
878
; ===========================================================================
879
; Construct one Huffman tree and assigns the code bit strings and lengths.
879
; Construct one Huffman tree and assigns the code bit strings and lengths.
880
; Update the total bit length for the current block.
880
; Update the total bit length for the current block.
881
; IN assertion: the field freq is set for all tree elements.
881
; IN assertion: the field freq is set for all tree elements.
882
; OUT assertions: the fields len and code are set to the optimal bit length
882
; OUT assertions: the fields len and code are set to the optimal bit length
883
;     and corresponding code. The length opt_len is updated; static_len is
883
;     and corresponding code. The length opt_len is updated; static_len is
884
;     also updated if stree is not null. The field max_code is set.
884
;     also updated if stree is not null. The field max_code is set.
885
 
885
 
886
;void (s, desc)
886
;void (s, desc)
887
;    deflate_state* s
887
;    deflate_state* s
888
;    tree_desc *desc ;the tree descriptor
888
;    tree_desc *desc ;the tree descriptor
889
align 4
889
align 4
890
proc build_tree uses eax ebx ecx edx edi, s:dword, desc:dword
890
proc build_tree uses eax ebx ecx edx edi, s:dword, desc:dword
891
locals
891
locals
892
	tree     dd  ? ;ct_data* ;= desc.dyn_tree
892
	tree     dd  ? ;ct_data* ;= desc.dyn_tree
893
	stree    dd  ? ;ct_data* ;= desc.stat_desc.static_tree
893
	stree    dd  ? ;ct_data* ;= desc.stat_desc.static_tree
894
	elems    dd  ? ;int      ;= desc.stat_desc.elems
894
	elems    dd  ? ;int      ;= desc.stat_desc.elems
895
	m        dd  ? ;int ;iterate over heap elements
895
	m        dd  ? ;int ;iterate over heap elements
896
	max_code dd -1 ;int ;largest code with non zero frequency
896
	max_code dd -1 ;int ;largest code with non zero frequency
897
	node     dd  ? ;int ;new node being created
897
	node     dd  ? ;int ;new node being created
898
endl
898
endl
899
	; Construct the initial heap, with least frequent element in
899
	; Construct the initial heap, with least frequent element in
900
	; heap[SMALLEST]. The sons of heap[n] are heap[2*n] and heap[2*n+1].
900
	; heap[SMALLEST]. The sons of heap[n] are heap[2*n] and heap[2*n+1].
901
	; heap[0] is not used.
901
	; heap[0] is not used.
902
	mov ebx,[desc]
902
	mov ebx,[desc]
903
	mov eax,[ebx+tree_desc.dyn_tree]
903
	mov eax,[ebx+tree_desc.dyn_tree]
904
	mov [tree],eax
904
	mov [tree],eax
905
	mov ecx,[ebx+tree_desc.stat_desc]
905
	mov ecx,[ebx+tree_desc.stat_desc]
906
	mov eax,[ecx+static_tree_desc.static_tree]
906
	mov eax,[ecx+static_tree_desc.static_tree]
907
	mov [stree],eax
907
	mov [stree],eax
908
	mov ecx,[ecx+static_tree_desc.elems]
908
	mov ecx,[ecx+static_tree_desc.elems]
909
	mov [elems],ecx
909
	mov [elems],ecx
910
	mov edi,[s]
910
	mov edi,[s]
911
	zlib_debug 'build_tree cycle0 ecx = %d',ecx
911
	zlib_debug 'build_tree cycle0 ecx = %d',ecx
912
 
912
 
913
	mov dword[edi+deflate_state.heap_len],0
913
	mov dword[edi+deflate_state.heap_len],0
914
	mov dword[edi+deflate_state.heap_max],HEAP_SIZE
914
	mov dword[edi+deflate_state.heap_max],HEAP_SIZE
915
 
915
 
916
	cmp ecx,0
-
 
917
	jle .cycle0end
916
	mov edx,[tree]
918
	xor edx,edx
917
	xor ecx,ecx
919
	.cycle0: ;for (..;..<..;..)
918
	.cycle0: ;for (..;..<..;..)
920
		mov eax,edx
-
 
921
		imul eax,sizeof.ct_data
919
	cmp ecx,[elems]
922
		add eax,[tree]
920
	jge .cycle0end
923
		cmp word[eax+Freq],0
921
		cmp word[edx+Freq],0
924
		je @f ;if (..!=0)
922
		je @f ;if (..!=0)
925
			inc dword[edi+deflate_state.heap_len]
923
			inc dword[edi+deflate_state.heap_len]
926
			mov eax,[edi+deflate_state.heap_len]
924
			mov eax,[edi+deflate_state.heap_len]
927
			mov [max_code],edx
925
			mov [max_code],ecx
928
			mov [edi+deflate_state.heap+2*eax],dx
926
			mov [edi+deflate_state.heap+2*eax],cx
929
			mov eax,edx
-
 
930
			add eax,edi
-
 
931
			add eax,deflate_state.depth
927
			mov byte[edi+deflate_state.depth+ecx],0
932
			mov byte[eax],0
-
 
933
			jmp .end0
928
			jmp .end0
934
align 4
929
align 4
935
		@@: ;else
930
		@@: ;else
936
			mov word[eax+Len],0
931
			mov word[edx+Len],0
937
		.end0:
932
		.end0:
-
 
933
		add edx,sizeof.ct_data
938
		inc edx
934
		inc ecx
939
		loop .cycle0
935
		jmp .cycle0
940
align 4
936
align 4
941
	.cycle0end:
937
	.cycle0end:
942
 
938
 
943
	; The pkzip format requires that at least one distance code exists,
939
	; The pkzip format requires that at least one distance code exists,
944
	; and that at least one bit should be sent even if there is only one
940
	; and that at least one bit should be sent even if there is only one
945
	; possible code. So to avoid special checks later on we force at least
941
	; possible code. So to avoid special checks later on we force at least
946
	; two codes of non zero frequency.
942
	; two codes of non zero frequency.
947
 
943
 
948
	.cycle1: ;while (..<..)
944
	.cycle1: ;while (..<..)
949
		cmp dword[edi+deflate_state.heap_len],2
945
		cmp dword[edi+deflate_state.heap_len],2
950
		jge .cycle1end
946
		jge .cycle1end
951
		inc dword[edi+deflate_state.heap_len]
947
		inc dword[edi+deflate_state.heap_len]
952
		xor eax,eax
948
		xor eax,eax
953
		cmp dword[max_code],2
949
		cmp dword[max_code],2
954
		jge @f
950
		jge @f
955
			inc dword[max_code]
951
			inc dword[max_code]
956
			mov eax,[max_code]
952
			mov eax,[max_code]
957
		@@:
953
		@@:
958
		mov ecx,[edi+deflate_state.heap_len]
954
		mov ecx,[edi+deflate_state.heap_len]
959
		mov [edi+deflate_state.heap+2*ecx],ax
955
		mov [edi+deflate_state.heap+2*ecx],ax
960
		mov [node],eax
956
		mov [node],eax
961
		imul eax,sizeof.ct_data
957
		imul eax,sizeof.ct_data
962
		add eax,[tree]
958
		add eax,[tree]
963
		mov word[eax+Freq],1
959
		mov word[eax+Freq],1
964
		mov eax,[node]
960
		mov eax,[node]
965
		mov byte[edi+deflate_state.depth+eax],0
961
		mov byte[edi+deflate_state.depth+eax],0
966
		dec dword[edi+deflate_state.opt_len]
962
		dec dword[edi+deflate_state.opt_len]
967
		cmp dword[stree],0
963
		cmp dword[stree],0
968
		je .cycle1 ;if (..)
964
		je .cycle1 ;if (..)
969
			mov eax,[node]
965
			mov eax,[node]
970
			imul eax,sizeof.ct_data
966
			imul eax,sizeof.ct_data
971
			add eax,[stree]
967
			add eax,[stree]
972
			movzx eax,word[eax+Len]
968
			movzx eax,word[eax+Len]
973
			sub [edi+deflate_state.static_len],eax
969
			sub [edi+deflate_state.static_len],eax
974
		; node is 0 or 1 so it does not have extra bits
970
		; node is 0 or 1 so it does not have extra bits
975
		jmp .cycle1
971
		jmp .cycle1
976
align 4
972
align 4
977
	.cycle1end:
973
	.cycle1end:
978
	mov eax,[max_code]
974
	mov eax,[max_code]
979
	mov [ebx+tree_desc.max_code],eax
975
	mov [ebx+tree_desc.max_code],eax
980
 
976
 
981
	; The elements heap[heap_len/2+1 .. heap_len] are leaves of the tree,
977
	; The elements heap[heap_len/2+1 .. heap_len] are leaves of the tree,
982
	; establish sub-heaps of increasing lengths:
978
	; establish sub-heaps of increasing lengths:
983
 
979
 
984
	mov ecx,[edi+deflate_state.heap_len]
980
	mov ecx,[edi+deflate_state.heap_len]
985
	shr ecx,1
981
	shr ecx,1
986
	.cycle2: ;for (..;..>=..;..)
982
	.cycle2: ;for (..;..>=..;..)
987
		cmp ecx,1
983
		cmp ecx,1
988
		jl .cycle2end
984
		jl .cycle2end
989
		stdcall pqdownheap, edi, [tree], ecx
985
		stdcall pqdownheap, edi, [tree], ecx
990
		dec ecx
986
		dec ecx
991
		jmp .cycle2
987
		jmp .cycle2
992
align 4
988
align 4
993
	.cycle2end:
989
	.cycle2end:
994
 
990
 
995
	; Construct the Huffman tree by repeatedly combining the least two
991
	; Construct the Huffman tree by repeatedly combining the least two
996
	; frequent nodes.
992
	; frequent nodes.
997
 
993
 
998
	mov eax,[elems]
994
	mov eax,[elems]
999
	mov [node],eax ;next internal node of the tree
995
	mov [node],eax ;next internal node of the tree
1000
	.cycle3: ;do
996
	.cycle3: ;do
1001
		pqremove edi, [tree], ecx ;n = node of least frequency
997
		pqremove edi, [tree], ecx ;n = node of least frequency
1002
		movzx edx,word[eax]
998
		movzx edx,word[eax]
1003
		mov [m],edx ;m = node of next least frequency
999
		mov [m],edx ;m = node of next least frequency
1004
 
1000
 
1005
		mov eax,[edi+deflate_state.heap_max]
1001
		mov eax,[edi+deflate_state.heap_max]
1006
		dec eax
1002
		dec eax
1007
		mov [edi+deflate_state.heap+2*eax],cx ;keep the nodes sorted by frequency
1003
		mov [edi+deflate_state.heap+2*eax],cx ;keep the nodes sorted by frequency
1008
		dec eax
1004
		dec eax
1009
		mov [edi+deflate_state.heap_max],eax
1005
		mov [edi+deflate_state.heap_max],eax
1010
		mov [edi+deflate_state.heap+2*eax],dx
1006
		mov [edi+deflate_state.heap+2*eax],dx
1011
 
1007
 
1012
		; Create a new node father of n and m
1008
		; Create a new node father of n and m
1013
		;;mov edx,[m]
1009
		;;mov edx,[m]
1014
		imul edx,sizeof.ct_data
1010
		imul edx,sizeof.ct_data
1015
		add edx,[tree]
1011
		add edx,[tree]
1016
		mov ax,word[edx+Freq]
1012
		mov ax,word[edx+Freq]
1017
		mov edx,ecx
1013
		mov edx,ecx
1018
		imul edx,sizeof.ct_data
1014
		imul edx,sizeof.ct_data
1019
		add edx,[tree]
1015
		add edx,[tree]
1020
		add ax,word[edx+Freq]
1016
		add ax,word[edx+Freq]
1021
		mov edx,[node]
1017
		mov edx,[node]
1022
		imul edx,sizeof.ct_data
1018
		imul edx,sizeof.ct_data
1023
		add edx,[tree]
1019
		add edx,[tree]
1024
		mov word[edx+Freq],ax
1020
		mov word[edx+Freq],ax
1025
 
1021
 
1026
		mov eax,ecx
1022
		mov eax,ecx
1027
		add eax,edi
1023
		add eax,edi
1028
		add eax,deflate_state.depth
1024
		mov al,byte[eax+deflate_state.depth]
1029
		mov al,byte[eax]
-
 
1030
		mov edx,[m]
1025
		mov edx,[m]
1031
		add edx,edi
1026
		add edx,edi
1032
		add edx,deflate_state.depth
1027
		mov ah,byte[edx+deflate_state.depth]
1033
		mov ah,byte[edx]
-
 
1034
		cmp al,ah
1028
		cmp al,ah
1035
		jl @f ;if (al>=ah) al=al : al=ah
1029
		jl @f ;if (al>=ah) al=al : al=ah
1036
			mov al,ah
1030
			mov al,ah
1037
		@@:
1031
		@@:
1038
		inc al
1032
		inc al
1039
		mov edx,[node]
1033
		mov edx,[node]
1040
		add edx,edi
1034
		add edx,edi
1041
		add edx,deflate_state.depth
1035
		mov byte[edx+deflate_state.depth],al
1042
		mov byte[edx],al
-
 
1043
 
1036
 
1044
		mov eax,[node]
1037
		mov eax,[node]
1045
		mov edx,[m]
1038
		mov edx,[m]
1046
		imul edx,sizeof.ct_data
1039
		imul edx,sizeof.ct_data
1047
		add edx,[tree]
1040
		add edx,[tree]
1048
		mov [edx+Dad],ax
1041
		mov [edx+Dad],ax
1049
		mov edx,ecx
1042
		mov edx,ecx
1050
		imul edx,sizeof.ct_data
1043
		imul edx,sizeof.ct_data
1051
		add edx,[tree]
1044
		add edx,[tree]
1052
		mov [edx+Dad],ax
1045
		mov [edx+Dad],ax
1053
;if DUMP_BL_TREE eq 1
1046
;if DUMP_BL_TREE eq 1
1054
;        if (tree == s->bl_tree) {
1047
;        if (tree == s->bl_tree) {
1055
;            fprintf(stderr,"\nnode %d(%d), sons %d(%d) %d(%d)",
1048
;            fprintf(stderr,"\nnode %d(%d), sons %d(%d) %d(%d)",
1056
;                    node, tree[node].Freq, n, tree[n].Freq, m, tree[m].Freq);
1049
;                    node, tree[node].Freq, n, tree[n].Freq, m, tree[m].Freq);
1057
;        }
1050
;        }
1058
;end if
1051
;end if
1059
		; and insert the new node in the heap
1052
		; and insert the new node in the heap
1060
		mov ecx,[node]
1053
		mov ecx,[node]
1061
		mov [edi+deflate_state.heap+2*SMALLEST],cx
1054
		mov [edi+deflate_state.heap+2*SMALLEST],cx
1062
		inc dword[node]
1055
		inc dword[node]
1063
		stdcall pqdownheap, edi, [tree], SMALLEST
1056
		stdcall pqdownheap, edi, [tree], SMALLEST
1064
		cmp dword[edi+deflate_state.heap_len],2
1057
		cmp dword[edi+deflate_state.heap_len],2
1065
		jge .cycle3 ;while (..>=..)
1058
		jge .cycle3 ;while (..>=..)
1066
 
1059
 
1067
	mov cx,[edi+deflate_state.heap+2*SMALLEST]
1060
	mov cx,[edi+deflate_state.heap+2*SMALLEST]
1068
	dec dword[edi+deflate_state.heap_max]
1061
	dec dword[edi+deflate_state.heap_max]
1069
	mov eax,[edi+deflate_state.heap_max]
1062
	mov eax,[edi+deflate_state.heap_max]
1070
	mov [edi+deflate_state.heap+2*eax],cx
1063
	mov [edi+deflate_state.heap+2*eax],cx
1071
 
1064
 
1072
	; At this point, the fields freq and dad are set. We can now
1065
	; At this point, the fields freq and dad are set. We can now
1073
	; generate the bit lengths.
1066
	; generate the bit lengths.
1074
 
1067
 
1075
	stdcall gen_bitlen, edi, [desc]
1068
	stdcall gen_bitlen, edi, [desc]
1076
 
1069
 
1077
	; The field len is now set, we can generate the bit codes
1070
	; The field len is now set, we can generate the bit codes
1078
	mov eax,edi
1071
	mov eax,edi
1079
	add eax,deflate_state.bl_count
1072
	add eax,deflate_state.bl_count
1080
	stdcall gen_codes, [tree], [max_code], eax
1073
	stdcall gen_codes, [tree], [max_code], eax
1081
	ret
1074
	ret
1082
endp
1075
endp
1083
 
1076
 
1084
; ===========================================================================
1077
; ===========================================================================
1085
; Scan a literal or distance tree to determine the frequencies of the codes
1078
; Scan a literal or distance tree to determine the frequencies of the codes
1086
; in the bit length tree.
1079
; in the bit length tree.
1087
 
1080
 
1088
;void (s, tree, max_code)
1081
;void (s, tree, max_code)
1089
;    deflate_state* s
1082
;    deflate_state* s
1090
;    ct_data *tree ;the tree to be scanned
1083
;    ct_data *tree ;the tree to be scanned
1091
;    int max_code  ;and its largest code of non zero frequency
1084
;    int max_code  ;and its largest code of non zero frequency
1092
align 4
1085
align 4
1093
proc scan_tree uses eax ebx ecx edi, s:dword, tree:dword, max_code:dword
1086
proc scan_tree uses eax ebx ecx edi, s:dword, tree:dword, max_code:dword
1094
locals
1087
locals
1095
	n dd ? ;int ;iterates over all tree elements
1088
	n dd ? ;int ;iterates over all tree elements
1096
	prevlen  dd -1 ;int ;last emitted length
1089
	prevlen  dd -1 ;int ;last emitted length
1097
	curlen    dd ? ;int ;length of current code
1090
	curlen    dd ? ;int ;length of current code
1098
	nextlen   dd ? ;int ;= tree[0].Len ;length of next code
1091
	nextlen   dd ? ;int ;= tree[0].Len ;length of next code
1099
	count     dd 0 ;int ;repeat count of the current code
1092
	count     dd 0 ;int ;repeat count of the current code
1100
	max_count dd 7 ;int ;max repeat count
1093
	max_count dd 7 ;int ;max repeat count
1101
	min_count dd 4 ;int ;min repeat count
1094
	min_count dd 4 ;int ;min repeat count
1102
endl
1095
endl
1103
	mov edi,[s]
1096
	mov edi,[s]
1104
	zlib_debug 'scan_tree'
1097
	zlib_debug 'scan_tree'
1105
	mov eax,[tree]
1098
	mov eax,[tree]
1106
	movzx eax,word[eax+Len]
1099
	movzx eax,word[eax+Len]
1107
	mov [nextlen],eax
1100
	mov [nextlen],eax
1108
	cmp eax,0
1101
	cmp eax,0
1109
	jne @f ;if (..==0)
1102
	jne @f ;if (..==0)
1110
		mov dword[max_count],138
1103
		mov dword[max_count],138
1111
		mov dword[min_count],3
1104
		mov dword[min_count],3
1112
	@@:
1105
	@@:
1113
	mov eax,[max_code]
1106
	mov eax,[max_code]
1114
	inc eax
1107
	inc eax
1115
	imul eax,sizeof.ct_data
1108
	imul eax,sizeof.ct_data
1116
	add eax,[tree]
1109
	add eax,[tree]
1117
	mov word[eax+Len],0xffff ;guard
1110
	mov word[eax+Len],0xffff ;guard
1118
 
1111
 
1119
	xor ecx,ecx
1112
	xor ecx,ecx
1120
	.cycle0:
1113
	.cycle0:
1121
		cmp ecx,[max_code]
1114
		cmp ecx,[max_code]
1122
		jg .cycle0end ;for (..;..<=..;..)
1115
		jg .cycle0end ;for (..;..<=..;..)
1123
		mov eax,[nextlen]
1116
		mov eax,[nextlen]
1124
		mov [curlen],eax
1117
		mov [curlen],eax
1125
		mov eax,ecx
1118
		mov eax,ecx
1126
		inc eax
1119
		inc eax
1127
		imul eax,sizeof.ct_data
1120
		imul eax,sizeof.ct_data
1128
		add eax,[tree]
1121
		add eax,[tree]
1129
		movzx eax,word[eax+Len]
1122
		movzx eax,word[eax+Len]
1130
		mov [nextlen],eax
1123
		mov [nextlen],eax
1131
		inc dword[count]
1124
		inc dword[count]
1132
		mov ebx,[count]
1125
		mov ebx,[count]
1133
		cmp ebx,[max_count]
1126
		cmp ebx,[max_count]
1134
		jge .end0
1127
		jge .end0
1135
		mov eax,[nextlen]
1128
		mov eax,[nextlen]
1136
		cmp [curlen],eax
1129
		cmp [curlen],eax
1137
		jne .end0 ;if (..<.. && ..==..)
1130
		jne .end0 ;if (..<.. && ..==..)
1138
			inc ecx
1131
			inc ecx
1139
			jmp .cycle0 ;continue
1132
			jmp .cycle0 ;continue
1140
		.end0:
1133
		.end0:
1141
		cmp ebx,[min_count]
1134
		cmp ebx,[min_count]
1142
		jge .end1 ;else if (..<..)
1135
		jge .end1 ;else if (..<..)
1143
			mov eax,[curlen]
1136
			mov eax,[curlen]
1144
			imul eax,sizeof.ct_data
1137
			imul eax,sizeof.ct_data
1145
			add eax,edi
1138
			add eax,edi
1146
			add eax,deflate_state.bl_tree+Freq
1139
			add word[eax+deflate_state.bl_tree+Freq],bx
1147
			add word[eax],bx
-
 
1148
			jmp .end4
1140
			jmp .end4
1149
		.end1:
1141
		.end1:
1150
		cmp dword[curlen],0
1142
		cmp dword[curlen],0
1151
		je .end2 ;else if (..!=0)
1143
		je .end2 ;else if (..!=0)
1152
			mov eax,[curlen]
1144
			mov eax,[curlen]
1153
			cmp eax,[prevlen]
1145
			cmp eax,[prevlen]
1154
			je @f ;if (..!=..)
1146
			je @f ;if (..!=..)
1155
				imul eax,sizeof.ct_data
1147
				imul eax,sizeof.ct_data
1156
				add eax,edi
1148
				add eax,edi
1157
				add eax,deflate_state.bl_tree+Freq
1149
				inc word[eax+deflate_state.bl_tree+Freq]
1158
				inc word[eax]
-
 
1159
			@@:
1150
			@@:
1160
			mov eax,REP_3_6
1151
			mov eax,REP_3_6
1161
			imul eax,sizeof.ct_data
1152
			imul eax,sizeof.ct_data
1162
			add eax,edi
1153
			add eax,edi
1163
			add eax,deflate_state.bl_tree+Freq
1154
			inc word[eax+deflate_state.bl_tree+Freq]
1164
			inc word[eax]
-
 
1165
			jmp .end4
1155
			jmp .end4
1166
		.end2:
1156
		.end2:
1167
		cmp ebx,10
1157
		cmp ebx,10
1168
		jg .end3 ;else if (..<=..)
1158
		jg .end3 ;else if (..<=..)
1169
			mov eax,REPZ_3_10
1159
			mov eax,REPZ_3_10
1170
			imul eax,sizeof.ct_data
1160
			imul eax,sizeof.ct_data
1171
			add eax,edi
1161
			add eax,edi
1172
			add eax,deflate_state.bl_tree+Freq
1162
			inc word[eax+deflate_state.bl_tree+Freq]
1173
			inc word[eax]
-
 
1174
			jmp .end4
1163
			jmp .end4
1175
		.end3: ;else
1164
		.end3: ;else
1176
			mov eax,REPZ_11_138
1165
			mov eax,REPZ_11_138
1177
			imul eax,sizeof.ct_data
1166
			imul eax,sizeof.ct_data
1178
			add eax,edi
1167
			add eax,edi
1179
			add eax,deflate_state.bl_tree+Freq
1168
			inc word[eax+deflate_state.bl_tree+Freq]
1180
			inc word[eax]
-
 
1181
		.end4:
1169
		.end4:
1182
		mov dword[curlen],0
1170
		mov dword[curlen],0
1183
		mov eax,[curlen]
1171
		mov eax,[curlen]
1184
		mov [prevlen],eax
1172
		mov [prevlen],eax
1185
		mov [nextlen],eax
1173
		mov [nextlen],eax
1186
		cmp eax,0
1174
		cmp eax,0
1187
		jne .end5 ;if (..==0)
1175
		jne .end5 ;if (..==0)
1188
			mov dword[max_count],138
1176
			mov dword[max_count],138
1189
			mov dword[min_count],3
1177
			mov dword[min_count],3
1190
			jmp .end7
1178
			jmp .end7
1191
		.end5:
1179
		.end5:
1192
		mov eax,[curlen]
1180
		mov eax,[curlen]
1193
		cmp eax,[nextlen]
1181
		cmp eax,[nextlen]
1194
		jne .end6 ;else if (..==..)
1182
		jne .end6 ;else if (..==..)
1195
			mov dword[max_count],6
1183
			mov dword[max_count],6
1196
			mov dword[min_count],3
1184
			mov dword[min_count],3
1197
			jmp .end7
1185
			jmp .end7
1198
		.end6: ;else
1186
		.end6: ;else
1199
			mov dword[max_count],7
1187
			mov dword[max_count],7
1200
			mov dword[min_count],4
1188
			mov dword[min_count],4
1201
		.end7:
1189
		.end7:
1202
		inc ecx
1190
		inc ecx
1203
		jmp .cycle0
1191
		jmp .cycle0
1204
	.cycle0end:
1192
	.cycle0end:
1205
	ret
1193
	ret
1206
endp
1194
endp
1207
 
1195
 
1208
; ===========================================================================
1196
; ===========================================================================
1209
; Send a literal or distance tree in compressed form, using the codes in
1197
; Send a literal or distance tree in compressed form, using the codes in
1210
; bl_tree.
1198
; bl_tree.
1211
 
1199
 
1212
;void (s, tree, max_code)
1200
;void (s, tree, max_code)
1213
;    deflate_state* s
1201
;    deflate_state* s
1214
;    ct_data *tree ;the tree to be scanned
1202
;    ct_data *tree ;the tree to be scanned
1215
;    int max_code  ;and its largest code of non zero frequency
1203
;    int max_code  ;and its largest code of non zero frequency
1216
align 4
1204
align 4
1217
proc send_tree uses eax ebx ecx edi, s:dword, tree:dword, max_code:dword
1205
proc send_tree uses eax ebx ecx edi, s:dword, tree:dword, max_code:dword
1218
locals
1206
locals
1219
	n dd ? ;int ;iterates over all tree elements
1207
	n dd ? ;int ;iterates over all tree elements
1220
	prevlen  dd -1 ;int ;last emitted length
1208
	prevlen  dd -1 ;int ;last emitted length
1221
	curlen    dd ? ;int ;length of current code
1209
	curlen    dd ? ;int ;length of current code
1222
	nextlen   dd ? ;int ;= tree[0].Len ;length of next code
1210
	nextlen   dd ? ;int ;= tree[0].Len ;length of next code
1223
	count     dd 0 ;int ;repeat count of the current code
1211
	count     dd 0 ;int ;repeat count of the current code
1224
	max_count dd 7 ;int ;max repeat count
1212
	max_count dd 7 ;int ;max repeat count
1225
	min_count dd 4 ;int ;min repeat count
1213
	min_count dd 4 ;int ;min repeat count
1226
endl
1214
endl
1227
	mov edi,[s]
1215
	mov edi,[s]
1228
	zlib_debug 'send_tree'
1216
	zlib_debug 'send_tree'
1229
	; *** tree[max_code+1].Len = -1 ;guard already set
1217
	; *** tree[max_code+1].Len = -1 ;guard already set
1230
	mov eax,[tree]
1218
	mov eax,[tree]
1231
	movzx eax,word[eax+Len]
1219
	movzx eax,word[eax+Len]
1232
	mov [nextlen],eax
1220
	mov [nextlen],eax
-
 
1221
	xor ecx,ecx
1233
	cmp eax,0
1222
	test eax,eax
1234
	jne @f ;if (..==0)
1223
	jnz .cycle0 ;if (..==0)
1235
		mov dword[max_count],138
1224
		mov dword[max_count],138
1236
		mov dword[min_count],3
1225
		mov dword[min_count],3
1237
	@@:
-
 
1238
 
1226
 
1239
	xor ecx,ecx
1227
align 4
1240
	.cycle0: ;for (..;..<=..;..)
1228
	.cycle0: ;for (..;..<=..;..)
1241
	cmp ecx,[max_code]
1229
	cmp ecx,[max_code]
1242
	jg .cycle0end
1230
	jg .cycle0end
1243
		mov eax,[nextlen]
1231
		mov eax,[nextlen]
1244
		mov [curlen],eax
1232
		mov [curlen],eax
1245
		mov eax,ecx
1233
		mov eax,ecx
1246
		inc eax
1234
		inc eax
1247
		imul eax,sizeof.ct_data
1235
		imul eax,sizeof.ct_data
1248
		add eax,[tree]
1236
		add eax,[tree]
1249
		movzx eax,word[eax+Len]
1237
		movzx eax,word[eax+Len]
1250
		mov [nextlen],eax
1238
		mov [nextlen],eax
1251
		inc dword[count]
1239
		inc dword[count]
1252
		mov ebx,[count]
1240
		mov ebx,[count]
1253
		cmp ebx,[max_count]
1241
		cmp ebx,[max_count]
1254
		jge .end0
1242
		jge .end0
1255
		mov eax,[nextlen]
1243
		mov eax,[nextlen]
1256
		cmp [curlen],eax
1244
		cmp [curlen],eax
1257
		jne .end0 ;if (..<.. && ..==..)
1245
		jne .end0 ;if (..<.. && ..==..)
1258
			inc ecx
1246
			inc ecx
1259
			jmp .cycle0 ;continue
1247
			jmp .cycle0 ;continue
-
 
1248
align 4
1260
		.end0:
1249
		.end0:
1261
		cmp ebx,[min_count]
1250
		cmp ebx,[min_count]
1262
		jge .end1 ;else if (..<..)
1251
		jge .end1 ;else if (..<..)
1263
			@@: ;do
1252
			@@: ;do
1264
				mov ebx,edi
1253
				mov ebx,edi
1265
				add ebx,deflate_state.bl_tree
1254
				add ebx,deflate_state.bl_tree
1266
				send_code edi, [curlen], ebx
1255
				send_code edi, [curlen], ebx
1267
				dec dword[count]
1256
				dec dword[count]
1268
				cmp dword[count],0
-
 
1269
				jne @b ;while (..!=0)
1257
				jnz @b ;while (..!=0)
1270
			jmp .end4
1258
			jmp .end4
1271
align 4
1259
align 4
1272
		.end1:
1260
		.end1:
1273
		cmp dword[curlen],0
1261
		cmp dword[curlen],0
1274
		je .end2 ;else if (..!=0)
1262
		je .end2 ;else if (..!=0)
1275
			mov eax,[curlen]
1263
			mov eax,[curlen]
1276
			cmp eax,[prevlen]
1264
			cmp eax,[prevlen]
1277
			je @f ;if (..!=..)
1265
			je @f ;if (..!=..)
1278
				mov ebx,edi
1266
				mov ebx,edi
1279
				add ebx,deflate_state.bl_tree
1267
				add ebx,deflate_state.bl_tree
1280
				send_code edi, eax, ebx
1268
				send_code edi, eax, ebx
1281
				dec dword[count]
1269
				dec dword[count]
1282
			@@:
1270
			@@:
1283
			cmp dword[count],3
1271
			cmp dword[count],3
1284
			jl @f
1272
			jl @f
1285
			cmp dword[count],6
1273
			cmp dword[count],6
1286
			jle .end8
1274
			jle .end8
1287
			@@:
1275
			@@:
1288
				zlib_assert ' 3_6?' ;Assert(..>=.. && ..<=..)
1276
				zlib_assert ' 3_6?' ;Assert(..>=.. && ..<=..)
1289
			.end8:
1277
			.end8:
1290
			mov ebx,edi
1278
			mov ebx,edi
1291
			add ebx,deflate_state.bl_tree
1279
			add ebx,deflate_state.bl_tree
1292
			send_code edi, REP_3_6, ebx
1280
			send_code edi, REP_3_6, ebx
1293
			mov ebx,[count]
1281
			mov ebx,[count]
1294
			sub ebx,3
1282
			sub ebx,3
1295
			stdcall send_bits, edi, ebx, 2
1283
			stdcall send_bits, edi, ebx, 2
1296
			jmp .end4
1284
			jmp .end4
1297
		.end2:
1285
		.end2:
1298
		cmp ebx,10
1286
		cmp ebx,10
1299
		jg .end3 ;else if (..<=..)
1287
		jg .end3 ;else if (..<=..)
1300
			mov ebx,edi
1288
			mov ebx,edi
1301
			add ebx,deflate_state.bl_tree
1289
			add ebx,deflate_state.bl_tree
1302
			send_code edi, REPZ_3_10, ebx
1290
			send_code edi, REPZ_3_10, ebx
1303
			mov ebx,[count]
1291
			mov ebx,[count]
1304
			sub ebx,3
1292
			sub ebx,3
1305
			stdcall send_bits, edi, ebx, 3
1293
			stdcall send_bits, edi, ebx, 3
1306
			jmp .end4
1294
			jmp .end4
1307
		.end3: ;else
1295
		.end3: ;else
1308
			mov ebx,edi
1296
			mov ebx,edi
1309
			add ebx,deflate_state.bl_tree
1297
			add ebx,deflate_state.bl_tree
1310
			send_code edi, REPZ_11_138, ebx
1298
			send_code edi, REPZ_11_138, ebx
1311
			mov ebx,[count]
1299
			mov ebx,[count]
1312
			sub ebx,11
1300
			sub ebx,11
1313
			stdcall send_bits, edi, ebx, 7
1301
			stdcall send_bits, edi, ebx, 7
1314
		.end4:
1302
		.end4:
1315
		mov dword[curlen],0
1303
		mov dword[curlen],0
1316
		mov eax,[curlen]
1304
		mov eax,[curlen]
1317
		mov [prevlen],eax
1305
		mov [prevlen],eax
1318
		mov [nextlen],eax
1306
		mov [nextlen],eax
1319
		cmp eax,0
1307
		cmp eax,0
1320
		jne .end5 ;if (..==0)
1308
		jne .end5 ;if (..==0)
1321
			mov dword[max_count],138
1309
			mov dword[max_count],138
1322
			mov dword[min_count],3
1310
			mov dword[min_count],3
1323
			jmp .end7
1311
			jmp .end7
1324
		.end5:
1312
		.end5:
1325
		mov eax,[curlen]
1313
		mov eax,[curlen]
1326
		cmp eax,[nextlen]
1314
		cmp eax,[nextlen]
1327
		jne .end6 ;else if (..==..)
1315
		jne .end6 ;else if (..==..)
1328
			mov dword[max_count],6
1316
			mov dword[max_count],6
1329
			mov dword[min_count],3
1317
			mov dword[min_count],3
1330
			jmp .end7
1318
			jmp .end7
1331
		.end6: ;else
1319
		.end6: ;else
1332
			mov dword[max_count],7
1320
			mov dword[max_count],7
1333
			mov dword[min_count],4
1321
			mov dword[min_count],4
1334
		.end7:
1322
		.end7:
1335
		inc ecx
1323
		inc ecx
1336
		jmp .cycle0
1324
		jmp .cycle0
1337
align 4
1325
align 4
1338
	.cycle0end:
1326
	.cycle0end:
1339
	ret
1327
	ret
1340
endp
1328
endp
1341
 
1329
 
1342
; ===========================================================================
1330
; ===========================================================================
1343
; Construct the Huffman tree for the bit lengths and return the index in
1331
; Construct the Huffman tree for the bit lengths and return the index in
1344
; bl_order of the last bit length code to send.
1332
; bl_order of the last bit length code to send.
1345
 
1333
 
1346
;int (s)
1334
;int (s)
1347
;    deflate_state* s
1335
;    deflate_state* s
1348
align 4
1336
align 4
1349
proc build_bl_tree uses edi, s:dword
1337
proc build_bl_tree uses edi, s:dword
1350
locals
1338
locals
1351
	max_blindex dd ? ;int ;index of last bit length code of non zero freq
1339
	max_blindex dd ? ;int ;index of last bit length code of non zero freq
1352
endl
1340
endl
1353
	mov edi,[s]
1341
	mov edi,[s]
1354
	; Determine the bit length frequencies for literal and distance trees
1342
	; Determine the bit length frequencies for literal and distance trees
1355
	mov eax,edi
1343
	mov eax,edi
1356
	add eax,deflate_state.dyn_ltree
1344
	add eax,deflate_state.dyn_ltree
1357
	stdcall scan_tree, edi, eax, [edi+deflate_state.l_desc.max_code]
1345
	stdcall scan_tree, edi, eax, [edi+deflate_state.l_desc.max_code]
1358
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
1346
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
1359
	stdcall scan_tree, edi, eax, [edi+deflate_state.d_desc.max_code]
1347
	stdcall scan_tree, edi, eax, [edi+deflate_state.d_desc.max_code]
1360
 
1348
 
1361
	; Build the bit length tree:
1349
	; Build the bit length tree:
1362
	add eax,deflate_state.bl_desc-deflate_state.dyn_dtree
1350
	add eax,deflate_state.bl_desc-deflate_state.dyn_dtree
1363
	stdcall build_tree, edi, eax
1351
	stdcall build_tree, edi, eax
1364
	; opt_len now includes the length of the tree representations, except
1352
	; opt_len now includes the length of the tree representations, except
1365
	; the lengths of the bit lengths codes and the 5+5+4 bits for the counts.
1353
	; the lengths of the bit lengths codes and the 5+5+4 bits for the counts.
1366
 
1354
 
1367
	; Determine the number of bit length codes to send. The pkzip format
1355
	; Determine the number of bit length codes to send. The pkzip format
1368
	; requires that at least 4 bit length codes be sent. (appnote.txt says
1356
	; requires that at least 4 bit length codes be sent. (appnote.txt says
1369
	; 3 but the actual value used is 4.)
1357
	; 3 but the actual value used is 4.)
1370
 
1358
 
1371
	mov dword[max_blindex],BL_CODES-1
1359
	mov dword[max_blindex],BL_CODES-1
1372
	.cycle0: ;for (..;..>=..;..)
1360
	.cycle0: ;for (..;..>=..;..)
1373
		cmp dword[max_blindex],3
1361
		cmp dword[max_blindex],3
1374
		jl .cycle0end
1362
		jl .cycle0end
1375
		dec dword[max_blindex]
1363
		dec dword[max_blindex]
1376
		mov eax,[max_blindex]
1364
		mov eax,[max_blindex]
1377
		add eax,bl_order
1365
		add eax,bl_order
1378
		movzx eax,byte[eax]
1366
		movzx eax,byte[eax]
1379
		imul eax,sizeof.ct_data
1367
		imul eax,sizeof.ct_data
1380
		add eax,edi
1368
		add eax,edi
1381
		add eax,deflate_state.bl_tree+Len
1369
		cmp word[eax+deflate_state.bl_tree+Len],0
1382
		cmp word[eax],0
-
 
1383
		jne .cycle0end ;if (..!=0) break
1370
		jne .cycle0end ;if (..!=0) break
1384
		jmp .cycle0
1371
		jmp .cycle0
-
 
1372
align 4
1385
	.cycle0end:
1373
	.cycle0end:
1386
	; Update opt_len to include the bit length tree and counts
1374
	; Update opt_len to include the bit length tree and counts
1387
	mov eax,[max_blindex]
1375
	mov eax,[max_blindex]
1388
	inc eax
1376
	inc eax
1389
	imul eax,3
1377
	imul eax,3
1390
	add eax,5+5+4
1378
	add eax,5+5+4
1391
	add [edi+deflate_state.opt_len],eax
1379
	add [edi+deflate_state.opt_len],eax
1392
;    Tracev((stderr, "\ndyn trees: dyn %ld, stat %ld", s->opt_len, s->static_len));
1380
;    Tracev((stderr, "\ndyn trees: dyn %ld, stat %ld", s->opt_len, s->static_len));
1393
 
1381
 
1394
	mov eax,[max_blindex]
1382
	mov eax,[max_blindex]
1395
	ret
1383
	ret
1396
endp
1384
endp
1397
 
1385
 
1398
; ===========================================================================
1386
; ===========================================================================
1399
; Send the header for a block using dynamic Huffman trees: the counts, the
1387
; Send the header for a block using dynamic Huffman trees: the counts, the
1400
; lengths of the bit length codes, the literal tree and the distance tree.
1388
; lengths of the bit length codes, the literal tree and the distance tree.
1401
; IN assertion: lcodes >= 257, dcodes >= 1, blcodes >= 4.
1389
; IN assertion: lcodes >= 257, dcodes >= 1, blcodes >= 4.
1402
 
1390
 
1403
;void (s, lcodes, dcodes, blcodes)
1391
;void (s, lcodes, dcodes, blcodes)
1404
;    deflate_state* s
1392
;    deflate_state* s
1405
;    int lcodes, dcodes, blcodes ;number of codes for each tree
1393
;    int lcodes, dcodes, blcodes ;number of codes for each tree
1406
align 4
1394
align 4
1407
proc send_all_trees uses eax ebx ecx edi, s:dword, lcodes:dword, dcodes:dword, blcodes:dword
1395
proc send_all_trees uses eax ebx ecx edi, s:dword, lcodes:dword, dcodes:dword, blcodes:dword
1408
;ecx = index in bl_order
1396
;ecx = index in bl_order
1409
	zlib_debug 'send_all_trees'
1397
	zlib_debug 'send_all_trees'
1410
	cmp dword[lcodes],257
1398
	cmp dword[lcodes],257
1411
	jl @f
1399
	jl @f
1412
	cmp dword[dcodes],1
1400
	cmp dword[dcodes],1
1413
	jl @f
1401
	jl @f
1414
	cmp dword[blcodes],4
1402
	cmp dword[blcodes],4
1415
	jge .end0
1403
	jge .end0
1416
	@@:
1404
	@@:
1417
		zlib_assert 'not enough codes' ;Assert(..>=.. && ..>=.. && ..>=..)
1405
		zlib_assert 'not enough codes' ;Assert(..>=.. && ..>=.. && ..>=..)
1418
	.end0:
1406
	.end0:
1419
	cmp dword[lcodes],L_CODES
1407
	cmp dword[lcodes],L_CODES
1420
	jg @f
1408
	jg @f
1421
	cmp dword[dcodes],D_CODES
1409
	cmp dword[dcodes],D_CODES
1422
	jg @f
1410
	jg @f
1423
	cmp dword[blcodes],BL_CODES
1411
	cmp dword[blcodes],BL_CODES
1424
	jle .end1
1412
	jle .end1
1425
	@@:
1413
	@@:
1426
		zlib_assert 'too many codes' ;Assert(..<=.. && ..<=.. && ..<=..)
1414
		zlib_assert 'too many codes' ;Assert(..<=.. && ..<=.. && ..<=..)
1427
	.end1:
1415
	.end1:
1428
;    Tracev((stderr, "\nbl counts: "));
1416
;    Tracev((stderr, "\nbl counts: "));
1429
	mov edi,[s]
1417
	mov edi,[s]
1430
	mov eax,[lcodes]
1418
	mov eax,[lcodes]
1431
	sub eax,257
1419
	sub eax,257
1432
	stdcall send_bits, edi, eax, 5 ;not +255 as stated in appnote.txt
1420
	stdcall send_bits, edi, eax, 5 ;not +255 as stated in appnote.txt
1433
	mov eax,[dcodes]
1421
	mov eax,[dcodes]
1434
	dec eax
1422
	dec eax
1435
	stdcall send_bits, edi, eax, 5
1423
	stdcall send_bits, edi, eax, 5
1436
	mov eax,[blcodes]
1424
	mov eax,[blcodes]
1437
	sub eax,4
1425
	sub eax,4
1438
	stdcall send_bits, edi, eax, 4 ;not -3 as stated in appnote.txt
1426
	stdcall send_bits, edi, eax, 4 ;not -3 as stated in appnote.txt
1439
	xor ecx,ecx
1427
	xor ecx,ecx
1440
	.cycle0:
1428
	.cycle0:
1441
		cmp ecx,[blcodes]
1429
		cmp ecx,[blcodes]
1442
		jge .cycle0end ;for (..;..<..;..)
1430
		jge .cycle0end ;for (..;..<..;..)
1443
;        Tracev((stderr, "\nbl code %2d ", bl_order[ecx]));
1431
;        Tracev((stderr, "\nbl code %2d ", bl_order[ecx]));
1444
		mov eax,ecx
1432
		mov eax,ecx
1445
		add eax,bl_order
1433
		add eax,bl_order
1446
		movzx eax,byte[eax]
1434
		movzx eax,byte[eax]
1447
		imul eax,sizeof.ct_data
1435
		imul eax,sizeof.ct_data
1448
		mov ebx,edi
1436
		add eax,edi
1449
		add ebx,deflate_state.bl_tree+Len
1437
		movzx eax,word[eax+deflate_state.bl_tree+Len]
1450
		add ebx,eax
-
 
1451
		stdcall send_bits, edi, ebx, 3
1438
		stdcall send_bits, edi, eax, 3
1452
		inc ecx
1439
		inc ecx
1453
		jmp .cycle0
1440
		jmp .cycle0
1454
align 4
1441
align 4
1455
	.cycle0end:
1442
	.cycle0end:
1456
;    Tracev((stderr, "\nbl tree: sent %ld", s->bits_sent));
1443
;    Tracev((stderr, "\nbl tree: sent %ld", s->bits_sent));
1457
 
1444
 
1458
	mov ebx,[lcodes]
1445
	mov ebx,[lcodes]
1459
	dec ebx
1446
	dec ebx
1460
	mov eax,edi
1447
	mov eax,edi
1461
	add eax,deflate_state.dyn_ltree
1448
	add eax,deflate_state.dyn_ltree
1462
	stdcall send_tree, edi, eax, ebx ;literal tree
1449
	stdcall send_tree, edi, eax, ebx ;literal tree
1463
;    Tracev((stderr, "\nlit tree: sent %ld", s->bits_sent));
1450
;    Tracev((stderr, "\nlit tree: sent %ld", s->bits_sent));
1464
 
1451
 
1465
	mov ebx,[dcodes]
1452
	mov ebx,[dcodes]
1466
	dec ebx
1453
	dec ebx
1467
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
1454
	add eax,deflate_state.dyn_dtree-deflate_state.dyn_ltree
1468
	stdcall send_tree, edi, eax, ebx ;distance tree
1455
	stdcall send_tree, edi, eax, ebx ;distance tree
1469
;    Tracev((stderr, "\ndist tree: sent %ld", s->bits_sent));
1456
;    Tracev((stderr, "\ndist tree: sent %ld", s->bits_sent));
1470
	ret
1457
	ret
1471
endp
1458
endp
1472
 
1459
 
1473
; ===========================================================================
1460
; ===========================================================================
1474
; Send a stored block
1461
; Send a stored block
1475
 
1462
 
1476
;void (s, buf, stored_len, last)
1463
;void (s, buf, stored_len, last)
1477
;    deflate_state* s
1464
;    deflate_state* s
1478
;    charf *buf     ;input block
1465
;    charf *buf     ;input block
1479
;    ulg stored_len ;length of input block
1466
;    ulg stored_len ;length of input block
1480
;    int last       ;one if this is the last block for a file
1467
;    int last       ;one if this is the last block for a file
1481
align 4
1468
align 4
1482
proc _tr_stored_block uses eax edi, s:dword, buf:dword, stored_len:dword, last:dword
1469
proc _tr_stored_block uses eax edi, s:dword, buf:dword, stored_len:dword, last:dword
1483
	mov edi,[s]
1470
	mov edi,[s]
1484
	mov eax,[last]
1471
	mov eax,[last]
1485
	add eax,STORED_BLOCK shl 1
1472
	add eax,STORED_BLOCK shl 1
1486
	stdcall send_bits, edi, eax, 3 ;send block type
1473
	stdcall send_bits, edi, eax, 3 ;send block type
1487
if DEBUG eq 1
1474
if DEBUG eq 1
1488
	mov eax,[edi+deflate_state.compressed_len]
1475
	mov eax,[edi+deflate_state.compressed_len]
1489
	add eax,3+7
1476
	add eax,3+7
1490
	and eax,not 7
1477
	and eax,not 7
1491
	mov [edi+deflate_state.compressed_len],eax
1478
	mov [edi+deflate_state.compressed_len],eax
1492
	mov eax,[stored_len]
1479
	mov eax,[stored_len]
1493
	add eax,4
1480
	add eax,4
1494
	shl eax,3
1481
	shl eax,3
1495
	add [edi+deflate_state.compressed_len],eax
1482
	add [edi+deflate_state.compressed_len],eax
1496
end if
1483
end if
1497
	stdcall copy_block, edi, [buf], [stored_len], 1 ;with header
1484
	stdcall copy_block, edi, [buf], [stored_len], 1 ;with header
1498
	ret
1485
	ret
1499
endp
1486
endp
1500
 
1487
 
1501
; ===========================================================================
1488
; ===========================================================================
1502
; Flush the bits in the bit buffer to pending output (leaves at most 7 bits)
1489
; Flush the bits in the bit buffer to pending output (leaves at most 7 bits)
1503
 
1490
 
1504
;void (s)
1491
;void (s)
1505
;    deflate_state* s
1492
;    deflate_state* s
1506
align 4
1493
align 4
1507
proc _tr_flush_bits, s:dword
1494
proc _tr_flush_bits, s:dword
1508
	stdcall bi_flush, [s]
1495
	stdcall bi_flush, [s]
1509
	ret
1496
	ret
1510
endp
1497
endp
1511
 
1498
 
1512
; ===========================================================================
1499
; ===========================================================================
1513
; Send one empty static block to give enough lookahead for inflate.
1500
; Send one empty static block to give enough lookahead for inflate.
1514
; This takes 10 bits, of which 7 may remain in the bit buffer.
1501
; This takes 10 bits, of which 7 may remain in the bit buffer.
1515
 
1502
 
1516
;void (s)
1503
;void (s)
1517
;    deflate_state* s
1504
;    deflate_state* s
1518
align 4
1505
align 4
1519
proc _tr_align uses edi, s:dword
1506
proc _tr_align uses edi, s:dword
1520
	mov edi,[s]
1507
	mov edi,[s]
1521
	stdcall send_bits, edi, STATIC_TREES shl 1, 3
1508
	stdcall send_bits, edi, STATIC_TREES shl 1, 3
1522
	send_code edi, END_BLOCK, static_ltree
1509
	send_code edi, END_BLOCK, static_ltree
1523
if DEBUG eq 1
1510
if DEBUG eq 1
1524
	add [edi+deflate_state.compressed_len],10 ;3 for block type, 7 for EOB
1511
	add [edi+deflate_state.compressed_len],10 ;3 for block type, 7 for EOB
1525
end if
1512
end if
1526
	stdcall bi_flush, edi
1513
	stdcall bi_flush, edi
1527
	ret
1514
	ret
1528
endp
1515
endp
1529
 
1516
 
1530
; ===========================================================================
1517
; ===========================================================================
1531
; Determine the best encoding for the current block: dynamic trees, static
1518
; Determine the best encoding for the current block: dynamic trees, static
1532
; trees or store, and output the encoded block to the zip file.
1519
; trees or store, and output the encoded block to the zip file.
1533
 
1520
 
1534
;void (s, buf, stored_len, last)
1521
;void (s, buf, stored_len, last)
1535
;    deflate_state* s
1522
;    deflate_state* s
1536
;    charf *buf     ;input block, or NULL if too old
1523
;    charf *buf     ;input block, or NULL if too old
1537
;    ulg stored_len ;length of input block
1524
;    ulg stored_len ;length of input block
1538
;    int last       ;one if this is the last block for a file
1525
;    int last       ;one if this is the last block for a file
1539
align 4
1526
align 4
1540
proc _tr_flush_block uses eax ebx edi, s:dword, buf:dword, stored_len:dword, last:dword
1527
proc _tr_flush_block uses eax ebx edi, s:dword, buf:dword, stored_len:dword, last:dword
1541
locals
1528
locals
1542
	opt_lenb dd ? ;ulg
1529
	opt_lenb dd ? ;ulg
1543
	static_lenb dd ? ;opt_len and static_len in bytes
1530
	static_lenb dd ? ;opt_len and static_len in bytes
1544
	max_blindex dd 0 ;int ;index of last bit length code of non zero freq
1531
	max_blindex dd 0 ;int ;index of last bit length code of non zero freq
1545
endl
1532
endl
1546
	; Build the Huffman trees unless a stored block is forced
1533
	; Build the Huffman trees unless a stored block is forced
1547
	mov edi,[s]
1534
	mov edi,[s]
1548
	zlib_debug '_tr_flush_block'
1535
	zlib_debug '_tr_flush_block'
1549
	cmp word[edi+deflate_state.level],0
1536
	cmp word[edi+deflate_state.level],0
1550
	jle .end0 ;if (..>0)
1537
	jle .end0 ;if (..>0)
1551
 
1538
 
1552
		; Check if the file is binary or text
1539
		; Check if the file is binary or text
1553
		mov ebx,[edi+deflate_state.strm]
1540
		mov ebx,[edi+deflate_state.strm]
1554
		cmp dword[ebx+z_stream.data_type],Z_UNKNOWN
1541
		cmp dword[ebx+z_stream.data_type],Z_UNKNOWN
1555
		jne @f ;if (..==..)
1542
		jne @f ;if (..==..)
1556
			stdcall detect_data_type, edi
1543
			stdcall detect_data_type, edi
1557
			mov [ebx+z_stream.data_type],eax
1544
			mov [ebx+z_stream.data_type],eax
1558
		@@:
1545
		@@:
1559
 
1546
 
1560
		; Construct the literal and distance trees
1547
		; Construct the literal and distance trees
1561
		mov eax,edi
1548
		mov eax,edi
1562
		add eax,deflate_state.l_desc
1549
		add eax,deflate_state.l_desc
1563
		stdcall build_tree, edi, eax
1550
		stdcall build_tree, edi, eax
1564
;        Tracev((stderr, "\nlit data: dyn %ld, stat %ld", s->opt_len, s->static_len));
1551
;        Tracev((stderr, "\nlit data: dyn %ld, stat %ld", s->opt_len, s->static_len));
1565
 
1552
 
1566
		mov eax,edi
1553
		mov eax,edi
1567
		add eax,deflate_state.d_desc
1554
		add eax,deflate_state.d_desc
1568
		stdcall build_tree, edi, eax
1555
		stdcall build_tree, edi, eax
1569
;        Tracev((stderr, "\ndist data: dyn %ld, stat %ld", s->opt_len, s->static_len));
1556
;        Tracev((stderr, "\ndist data: dyn %ld, stat %ld", s->opt_len, s->static_len));
1570
		; At this point, opt_len and static_len are the total bit lengths of
1557
		; At this point, opt_len and static_len are the total bit lengths of
1571
		; the compressed block data, excluding the tree representations.
1558
		; the compressed block data, excluding the tree representations.
1572
 
1559
 
1573
		; Build the bit length tree for the above two trees, and get the index
1560
		; Build the bit length tree for the above two trees, and get the index
1574
		; in bl_order of the last bit length code to send.
1561
		; in bl_order of the last bit length code to send.
1575
 
1562
 
1576
		stdcall build_bl_tree, edi
1563
		stdcall build_bl_tree, edi
1577
		mov [max_blindex],eax
1564
		mov [max_blindex],eax
1578
 
1565
 
1579
		; Determine the best encoding. Compute the block lengths in bytes.
1566
		; Determine the best encoding. Compute the block lengths in bytes.
1580
		mov eax,[edi+deflate_state.opt_len]
1567
		mov eax,[edi+deflate_state.opt_len]
1581
		add eax,3+7
1568
		add eax,3+7
1582
		shr eax,3
1569
		shr eax,3
1583
		mov [opt_lenb],eax
1570
		mov [opt_lenb],eax
1584
		mov eax,[edi+deflate_state.static_len]
1571
		mov eax,[edi+deflate_state.static_len]
1585
		add eax,3+7
1572
		add eax,3+7
1586
		shr eax,3
1573
		shr eax,3
1587
		mov [static_lenb],eax
1574
		mov [static_lenb],eax
1588
 
1575
 
1589
;        Tracev((stderr, "\nopt %lu(%lu) stat %lu(%lu) stored %lu lit %u ",
1576
;        Tracev((stderr, "\nopt %lu(%lu) stat %lu(%lu) stored %lu lit %u ",
1590
;                opt_lenb, s->opt_len, static_lenb, s->static_len, stored_len,
1577
;                opt_lenb, s->opt_len, static_lenb, s->static_len, stored_len,
1591
;                s->last_lit));
1578
;                s->last_lit));
1592
 
1579
 
1593
		cmp eax,[opt_lenb]
1580
		cmp eax,[opt_lenb]
1594
		jg .end1 ;if (..<=..)
1581
		jg .end1 ;if (..<=..)
1595
			mov [opt_lenb],eax
1582
			mov [opt_lenb],eax
1596
		jmp .end1
1583
		jmp .end1
1597
	.end0: ;else
1584
	.end0: ;else
1598
		cmp dword[buf],0
1585
		cmp dword[buf],0
1599
		jne @f
1586
		jne @f
1600
			zlib_assert 'lost buf' ;Assert(..!=0)
1587
			zlib_assert 'lost buf' ;Assert(..!=0)
1601
		@@:
1588
		@@:
1602
		mov eax,[stored_len]
1589
		mov eax,[stored_len]
1603
		add eax,5
1590
		add eax,5
1604
		mov [static_lenb],eax
1591
		mov [static_lenb],eax
1605
		mov [opt_lenb],eax ;force a stored block
1592
		mov [opt_lenb],eax ;force a stored block
1606
	.end1:
1593
	.end1:
1607
 
1594
 
1608
if FORCE_STORED eq 1
1595
if FORCE_STORED eq 1
1609
	cmp dword[buf],0
1596
	cmp dword[buf],0
1610
	je .end2 ;if (..!=0) ;force stored block
1597
	je .end2 ;if (..!=0) ;force stored block
1611
else
1598
else
1612
	mov eax,[stored_len]
1599
	mov eax,[stored_len]
1613
	add eax,4
1600
	add eax,4
1614
	cmp eax,[opt_lenb]
1601
	cmp eax,[opt_lenb]
1615
	jg .end2
1602
	jg .end2
1616
	cmp dword[buf],0
1603
	cmp dword[buf],0
1617
	je .end2 ;if (..<=.. && ..!=0)
1604
	je .end2 ;if (..<=.. && ..!=0)
1618
		;4: two words for the lengths
1605
		;4: two words for the lengths
1619
end if
1606
end if
1620
		; The test buf != NULL is only necessary if LIT_BUFSIZE > WSIZE.
1607
		; The test buf != NULL is only necessary if LIT_BUFSIZE > WSIZE.
1621
		; Otherwise we can't have processed more than WSIZE input bytes since
1608
		; Otherwise we can't have processed more than WSIZE input bytes since
1622
		; the last block flush, because compression would have been
1609
		; the last block flush, because compression would have been
1623
		; successful. If LIT_BUFSIZE <= WSIZE, it is never too late to
1610
		; successful. If LIT_BUFSIZE <= WSIZE, it is never too late to
1624
		; transform a block into a stored block.
1611
		; transform a block into a stored block.
1625
 
1612
 
1626
		stdcall _tr_stored_block, edi, [buf], [stored_len], [last]
1613
		stdcall _tr_stored_block, edi, [buf], [stored_len], [last]
1627
		jmp .end4
1614
		jmp .end4
1628
	.end2:
1615
	.end2:
1629
if FORCE_STATIC eq 1
1616
if FORCE_STATIC eq 1
1630
	cmp dword[static_lenb],0
1617
	cmp dword[static_lenb],0
1631
	jl .end3 ;else if (..>=0) ;force static trees
1618
	jl .end3 ;else if (..>=0) ;force static trees
1632
else
1619
else
1633
	cmp word[edi+deflate_state.strategy],Z_FIXED
1620
	cmp word[edi+deflate_state.strategy],Z_FIXED
1634
	je @f
1621
	je @f
1635
	mov eax,[opt_lenb]
1622
	mov eax,[opt_lenb]
1636
	cmp [static_lenb],eax
1623
	cmp [static_lenb],eax
1637
	je @f ;else if (..==.. || ..==..)
1624
	je @f ;else if (..==.. || ..==..)
1638
		jmp .end3
1625
		jmp .end3
1639
	@@:
1626
	@@:
1640
end if
1627
end if
1641
		mov eax,STATIC_TREES shl 1
1628
		mov eax,STATIC_TREES shl 1
1642
		add eax,[last]
1629
		add eax,[last]
1643
		stdcall send_bits, edi, eax, 3
1630
		stdcall send_bits, edi, eax, 3
1644
		stdcall compress_block, edi, static_ltree, static_dtree
1631
		stdcall compress_block, edi, static_ltree, static_dtree
1645
if DEBUG eq 1
1632
if DEBUG eq 1
1646
		mov eax,[edi+deflate_state.static_len]
1633
		mov eax,[edi+deflate_state.static_len]
1647
		add eax,3
1634
		add eax,3
1648
		add [edi+deflate_state.compressed_len],eax
1635
		add [edi+deflate_state.compressed_len],eax
1649
end if
1636
end if
1650
		jmp .end4
1637
		jmp .end4
1651
	.end3: ;else
1638
	.end3: ;else
1652
		mov eax,DYN_TREES shl 1
1639
		mov eax,DYN_TREES shl 1
1653
		add eax,[last]
1640
		add eax,[last]
1654
		stdcall send_bits, edi, eax, 3
1641
		stdcall send_bits, edi, eax, 3
1655
		mov eax,[max_blindex]
1642
		mov eax,[max_blindex]
1656
		inc eax
1643
		inc eax
1657
		push eax
1644
		push eax
1658
		mov eax,[edi+deflate_state.d_desc.max_code]
1645
		mov eax,[edi+deflate_state.d_desc.max_code]
1659
		inc eax
1646
		inc eax
1660
		push eax
1647
		push eax
1661
		mov eax,[edi+deflate_state.l_desc.max_code]
1648
		mov eax,[edi+deflate_state.l_desc.max_code]
1662
		inc eax
1649
		inc eax
1663
		stdcall send_all_trees, edi, eax ;, ..., ...
1650
		stdcall send_all_trees, edi, eax ;, ..., ...
1664
		mov eax,edi
1651
		mov eax,edi
1665
		add eax,deflate_state.dyn_dtree
1652
		add eax,deflate_state.dyn_dtree
1666
		push eax
1653
		push eax
1667
		add eax,deflate_state.dyn_ltree-deflate_state.dyn_dtree
1654
		add eax,deflate_state.dyn_ltree-deflate_state.dyn_dtree
1668
		stdcall compress_block, edi, eax ;, ...
1655
		stdcall compress_block, edi, eax ;, ...
1669
if DEBUG eq 1
1656
if DEBUG eq 1
1670
		mov eax,[edi+deflate_state.opt_len]
1657
		mov eax,[edi+deflate_state.opt_len]
1671
		add eax,3
1658
		add eax,3
1672
		add [edi+deflate_state.compressed_len],eax
1659
		add [edi+deflate_state.compressed_len],eax
1673
end if
1660
end if
1674
	.end4:
1661
	.end4:
1675
;    Assert (s->compressed_len == s->bits_sent, "bad compressed size");
1662
;    Assert (s->compressed_len == s->bits_sent, "bad compressed size");
1676
	; The above check is made mod 2^32, for files larger than 512 MB
1663
	; The above check is made mod 2^32, for files larger than 512 MB
1677
	; and uLong implemented on 32 bits.
1664
	; and uLong implemented on 32 bits.
1678
 
1665
 
1679
	stdcall init_block,edi
1666
	stdcall init_block,edi
1680
 
1667
 
1681
	cmp dword[last],0
1668
	cmp dword[last],0
1682
	je @f ;if (..)
1669
	je @f ;if (..)
1683
		stdcall bi_windup,edi
1670
		stdcall bi_windup,edi
1684
if DEBUG eq 1
1671
if DEBUG eq 1
1685
		add [edi+deflate_state.compressed_len],7 ;align on byte boundary
1672
		add [edi+deflate_state.compressed_len],7 ;align on byte boundary
1686
end if
1673
end if
1687
	@@:
1674
	@@:
1688
;    Tracev((stderr,"\ncomprlen %lu(%lu) ", s->compressed_len>>3,
1675
;    Tracev((stderr,"\ncomprlen %lu(%lu) ", s->compressed_len>>3,
1689
;           s->compressed_len-7*last));
1676
;           s->compressed_len-7*last));
1690
	ret
1677
	ret
1691
endp
1678
endp
1692
 
1679
 
1693
; ===========================================================================
1680
; ===========================================================================
1694
; Save the match info and tally the frequency counts. Return true if
1681
; Save the match info and tally the frequency counts. Return true if
1695
; the current block must be flushed.
1682
; the current block must be flushed.
1696
 
1683
 
1697
;int (s, dist, lc)
1684
;int (s, dist, lc)
1698
;    deflate_state* s
1685
;    deflate_state* s
1699
;    unsigned dist ;distance of matched string
1686
;    unsigned dist ;distance of matched string
1700
;    unsigned lc   ;match length-MIN_MATCH or unmatched char (if dist==0)
1687
;    unsigned lc   ;match length-MIN_MATCH or unmatched char (if dist==0)
1701
align 4
1688
align 4
1702
proc _tr_tally uses ebx edi, s:dword, dist:dword, lc:dword
1689
proc _tr_tally uses ebx edi, s:dword, dist:dword, lc:dword
1703
	mov edi,[s]
1690
	mov edi,[s]
1704
	zlib_debug '_tr_tally'
1691
	zlib_debug '_tr_tally'
1705
	mov eax,[edi+deflate_state.last_lit]
1692
	mov eax,[edi+deflate_state.last_lit]
1706
	shl eax,1
1693
	shl eax,1
1707
	add eax,[edi+deflate_state.d_buf]
1694
	add eax,[edi+deflate_state.d_buf]
1708
	mov ebx,[dist]
1695
	mov ebx,[dist]
1709
	mov word[eax],bx
1696
	mov word[eax],bx
1710
	mov eax,[edi+deflate_state.last_lit]
1697
	mov eax,[edi+deflate_state.last_lit]
1711
	add eax,[edi+deflate_state.l_buf]
1698
	add eax,[edi+deflate_state.l_buf]
1712
	mov ebx,[lc]
1699
	mov ebx,[lc]
1713
	mov byte[eax],bl
1700
	mov byte[eax],bl
1714
	inc dword[edi+deflate_state.last_lit]
1701
	inc dword[edi+deflate_state.last_lit]
1715
	cmp dword[dist],0
1702
	cmp dword[dist],0
1716
	jne @f ;if (..==0)
1703
	jne @f ;if (..==0)
1717
		; lc is the unmatched char
1704
		; lc is the unmatched char
1718
		mov eax,[lc]
1705
		mov eax,[lc]
1719
		imul eax,sizeof.ct_data
1706
		imul eax,sizeof.ct_data
1720
		add eax,edi
1707
		add eax,edi
1721
		inc word[eax+deflate_state.dyn_ltree+Freq]
1708
		inc word[eax+deflate_state.dyn_ltree+Freq]
1722
		jmp .end0
1709
		jmp .end0
1723
	@@: ;else
1710
	@@: ;else
1724
		inc dword[edi+deflate_state.matches]
1711
		inc dword[edi+deflate_state.matches]
1725
		; Here, lc is the match length - MIN_MATCH
1712
		; Here, lc is the match length - MIN_MATCH
1726
		dec dword[dist] ;dist = match distance - 1
1713
		dec dword[dist] ;dist = match distance - 1
1727
		MAX_DIST edi
1714
		MAX_DIST edi
1728
		cmp word[dist],ax
1715
		cmp word[dist],ax
1729
		jge @f
1716
		jge @f
1730
		cmp word[lc],MAX_MATCH-MIN_MATCH
1717
		cmp word[lc],MAX_MATCH-MIN_MATCH
1731
		jg @f
1718
		jg @f
1732
		d_code [dist]
1719
		d_code [dist]
1733
		cmp ax,D_CODES
1720
		cmp ax,D_CODES
1734
		jl .end2
1721
		jl .end2
1735
		@@:
1722
		@@:
1736
			zlib_assert '_tr_tally: bad match' ;Assert(..<.. && ..<=.. && ..<..)
1723
			zlib_assert '_tr_tally: bad match' ;Assert(..<.. && ..<=.. && ..<..)
1737
		.end2:
1724
		.end2:
1738
		mov eax,[lc]
1725
		mov eax,[lc]
1739
		add eax,_length_code
1726
		add eax,_length_code
1740
		movzx eax,byte[eax]
1727
		movzx eax,byte[eax]
1741
		add eax,LITERALS+1
1728
		add eax,LITERALS+1
1742
		imul eax,sizeof.ct_data
1729
		imul eax,sizeof.ct_data
1743
		add eax,edi
1730
		add eax,edi
1744
		inc word[eax+deflate_state.dyn_ltree+Freq]
1731
		inc word[eax+deflate_state.dyn_ltree+Freq]
1745
		d_code [dist]
1732
		d_code [dist]
1746
		imul eax,sizeof.ct_data
1733
		imul eax,sizeof.ct_data
1747
		add eax,edi
1734
		add eax,edi
1748
		inc word[eax+deflate_state.dyn_dtree+Freq]
1735
		inc word[eax+deflate_state.dyn_dtree+Freq]
1749
	.end0:
1736
	.end0:
1750
 
1737
 
1751
if TRUNCATE_BLOCK eq 1
1738
if TRUNCATE_BLOCK eq 1
1752
	; Try to guess if it is profitable to stop the current block here
1739
	; Try to guess if it is profitable to stop the current block here
1753
	mov eax,[edi+deflate_state.last_lit]
1740
	mov eax,[edi+deflate_state.last_lit]
1754
	and eax,0x1fff
1741
	and eax,0x1fff
1755
	cmp eax,0
1742
	cmp eax,0
1756
	jne .end1
1743
	jne .end1
1757
	cmp word[edi+deflate_state.level],2
1744
	cmp word[edi+deflate_state.level],2
1758
	jle .end1 ;if (..==.. && ..>..)
1745
	jle .end1 ;if (..==.. && ..>..)
1759
	; Compute an upper bound for the compressed length
1746
	; Compute an upper bound for the compressed length
1760
;        ulg out_length = (ulg)s->last_lit*8L;
1747
;        ulg out_length = (ulg)s->last_lit*8L;
1761
;        ulg in_length = (ulg)((long)s->strstart - s->block_start);
1748
;        ulg in_length = (ulg)((long)s->strstart - s->block_start);
1762
;        int dcode;
1749
;        int dcode;
1763
;        for (dcode = 0; dcode < D_CODES; dcode++) {
1750
;        for (dcode = 0; dcode < D_CODES; dcode++) {
1764
;            out_length += (ulg)s->dyn_dtree[dcode].Freq *
1751
;            out_length += (ulg)s->dyn_dtree[dcode].Freq *
1765
;                (5L+extra_dbits[dcode]);
1752
;                (5L+extra_dbits[dcode]);
1766
;        }
1753
;        }
1767
;        out_length >>= 3;
1754
;        out_length >>= 3;
1768
;        Tracev((stderr,"\nlast_lit %u, in %ld, out ~%ld(%ld%%) ",
1755
;        Tracev((stderr,"\nlast_lit %u, in %ld, out ~%ld(%ld%%) ",
1769
;               s->last_lit, in_length, out_length,
1756
;               s->last_lit, in_length, out_length,
1770
;               100L - out_length*100L/in_length));
1757
;               100L - out_length*100L/in_length));
1771
;        if (s->matches < s->last_lit/2 && out_length < in_length/2) return 1;
1758
;        if (s->matches < s->last_lit/2 && out_length < in_length/2) return 1;
1772
	.end1:
1759
	.end1:
1773
end if
1760
end if
1774
	mov ebx,[edi+deflate_state.last_lit]
1761
	mov ebx,[edi+deflate_state.last_lit]
1775
	mov edi,[edi+deflate_state.lit_bufsize]
1762
	mov edi,[edi+deflate_state.lit_bufsize]
1776
	dec edi
1763
	dec edi
1777
	xor eax,eax
1764
	xor eax,eax
1778
	cmp ebx,edi
1765
	cmp ebx,edi
1779
	jne @f
1766
	jne @f
1780
		inc eax ;return (..==..)
1767
		inc eax ;return (..==..)
1781
	@@:
1768
	@@:
1782
	; We avoid equality with lit_bufsize because of wraparound at 64K
1769
	; We avoid equality with lit_bufsize because of wraparound at 64K
1783
	; on 16 bit machines and because stored blocks are restricted to
1770
	; on 16 bit machines and because stored blocks are restricted to
1784
	; 64K-1 bytes.
1771
	; 64K-1 bytes.
1785
	ret
1772
	ret
1786
endp
1773
endp
1787
 
1774
 
1788
; ===========================================================================
1775
; ===========================================================================
1789
; Send the block data compressed using the given Huffman trees
1776
; Send the block data compressed using the given Huffman trees
1790
 
1777
 
1791
;void (s, ltree, dtree)
1778
;void (s, ltree, dtree)
1792
;    deflate_state* s
1779
;    deflate_state* s
1793
;    ct_data *ltree ;literal tree
1780
;    ct_data *ltree ;literal tree
1794
;    ct_data *dtree ;distance tree
1781
;    ct_data *dtree ;distance tree
1795
align 4
1782
align 4
1796
proc compress_block uses eax edi, s:dword, ltree:dword, dtree:dword
1783
proc compress_block uses eax edi, s:dword, ltree:dword, dtree:dword
1797
locals
1784
locals
1798
	dist  dd ? ;unsigned ;distance of matched string
1785
	dist  dd ? ;unsigned ;distance of matched string
1799
	lc    dd ? ;int      ;match length or unmatched char (if dist == 0)
1786
	lc    dd ? ;int      ;match length or unmatched char (if dist == 0)
1800
	lx    dd 0 ;unsigned ;running index in l_buf
1787
	lx    dd 0 ;unsigned ;running index in l_buf
1801
	u_code dd ? ;unsigned ;the code to send
1788
	u_code dd ? ;unsigned ;the code to send
1802
	extra  dd ? ;int      ;number of extra bits to send
1789
	extra  dd ? ;int      ;number of extra bits to send
1803
endl
1790
endl
1804
	mov edi,[s]
1791
	mov edi,[s]
1805
	cmp dword[edi+deflate_state.last_lit],0
1792
	cmp dword[edi+deflate_state.last_lit],0
1806
	je .end0 ;if (..!=0)
1793
	je .end0 ;if (..!=0)
1807
	.cycle0: ; do
1794
	.cycle0: ; do
1808
		mov eax,[lx]
1795
		mov eax,[lx]
1809
		shl eax,1
1796
		shl eax,1
1810
		add eax,[edi+deflate_state.d_buf]
1797
		add eax,[edi+deflate_state.d_buf]
1811
		movzx eax,word[eax]
1798
		movzx eax,word[eax]
1812
		mov [dist],eax
1799
		mov [dist],eax
1813
		mov eax,[lx]
1800
		mov eax,[lx]
1814
		add eax,[edi+deflate_state.l_buf]
1801
		add eax,[edi+deflate_state.l_buf]
1815
		movzx eax,byte[eax]
1802
		movzx eax,byte[eax]
1816
		mov [lc],eax
1803
		mov [lc],eax
1817
		inc dword[lx]
1804
		inc dword[lx]
1818
		cmp dword[dist],0
1805
		cmp dword[dist],0
1819
		jne @f ;if (..==0)
1806
		jne @f ;if (..==0)
1820
			send_code edi, [lc], [ltree] ;send a literal byte
1807
			send_code edi, [lc], [ltree] ;send a literal byte
1821
;            Tracecv(isgraph(lc), (stderr," '%c' ", lc));
1808
;            Tracecv(isgraph(lc), (stderr," '%c' ", lc));
1822
			jmp .end1
1809
			jmp .end1
1823
		@@: ;else
1810
		@@: ;else
1824
			; Here, lc is the match length - MIN_MATCH
1811
			; Here, lc is the match length - MIN_MATCH
1825
			mov eax,[lc]
1812
			mov eax,[lc]
1826
			add eax,_length_code
1813
			add eax,_length_code
1827
			movzx eax,byte[eax]
1814
			movzx eax,byte[eax]
1828
			mov [u_code],eax
1815
			mov [u_code],eax
1829
			add eax,LITERALS+1
1816
			add eax,LITERALS+1
1830
			send_code edi, eax, [ltree] ;send the length code
1817
			send_code edi, eax, [ltree] ;send the length code
1831
			mov eax,[u_code]
1818
			mov eax,[u_code]
1832
			shl eax,2
1819
			shl eax,2
1833
			add eax,extra_lbits
1820
			add eax,extra_lbits
1834
			mov eax,[eax]
1821
			mov eax,[eax]
1835
			mov [extra],eax
1822
			mov [extra],eax
1836
			cmp eax,0
1823
			cmp eax,0
1837
			je @f ;if (..!=0)
1824
			je @f ;if (..!=0)
1838
				mov eax,[u_code]
1825
				mov eax,[u_code]
1839
				shl eax,2
1826
				shl eax,2
1840
				add eax,base_length
1827
				add eax,base_length
1841
				mov eax,[eax]
1828
				mov eax,[eax]
1842
				sub [lc],eax
1829
				sub [lc],eax
1843
				stdcall send_bits, edi, [lc], [extra] ;send the extra length bits
1830
				stdcall send_bits, edi, [lc], [extra] ;send the extra length bits
1844
			@@:
1831
			@@:
1845
			dec dword[dist] ;dist is now the match distance - 1
1832
			dec dword[dist] ;dist is now the match distance - 1
1846
			d_code [dist]
1833
			d_code [dist]
1847
			mov [u_code],eax
1834
			mov [u_code],eax
1848
			cmp eax,D_CODES
1835
			cmp eax,D_CODES
1849
			jl @f
1836
			jl @f
1850
				zlib_assert 'bad d_code' ;Assert(..<..)
1837
				zlib_assert 'bad d_code' ;Assert(..<..)
1851
			@@:
1838
			@@:
1852
			send_code edi, [u_code], [dtree] ;send the distance code
1839
			send_code edi, [u_code], [dtree] ;send the distance code
1853
			mov eax,[u_code]
1840
			mov eax,[u_code]
1854
			shl eax,2
1841
			shl eax,2
1855
			add eax,extra_dbits
1842
			add eax,extra_dbits
1856
			mov eax,[eax]
1843
			mov eax,[eax]
1857
			mov [extra],eax
1844
			mov [extra],eax
1858
			cmp eax,0
1845
			cmp eax,0
1859
			je .end1 ;if (..!=0)
1846
			je .end1 ;if (..!=0)
1860
				mov eax,[u_code]
1847
				mov eax,[u_code]
1861
				shl eax,2
1848
				shl eax,2
1862
				add eax,base_dist
1849
				add eax,base_dist
1863
				mov eax,[eax]
1850
				mov eax,[eax]
1864
				sub [dist],eax
1851
				sub [dist],eax
1865
				stdcall send_bits, edi, [dist], [extra] ;send the extra distance bits
1852
				stdcall send_bits, edi, [dist], [extra] ;send the extra distance bits
1866
		.end1: ;literal or match pair ?
1853
		.end1: ;literal or match pair ?
1867
 
1854
 
1868
		; Check that the overlay between pending_buf and d_buf+l_buf is ok:
1855
		; Check that the overlay between pending_buf and d_buf+l_buf is ok:
1869
		mov eax,[lx]
1856
		mov eax,[lx]
1870
		shl eax,1
1857
		shl eax,1
1871
		add eax,[edi+deflate_state.lit_bufsize]
1858
		add eax,[edi+deflate_state.lit_bufsize]
1872
		cmp [edi+deflate_state.pending],eax
1859
		cmp [edi+deflate_state.pending],eax
1873
		jl @f
1860
		jl @f
1874
			zlib_assert 'pendingBuf overflow' ;Assert(..<..)
1861
			zlib_assert 'pendingBuf overflow' ;Assert(..<..)
1875
		@@:
1862
		@@:
1876
		mov eax,[edi+deflate_state.last_lit]
1863
		mov eax,[edi+deflate_state.last_lit]
1877
		cmp [lx],eax
1864
		cmp [lx],eax
1878
		jl .cycle0 ;while (..<..)
1865
		jl .cycle0 ;while (..<..)
1879
align 4
1866
align 4
1880
	.end0:
1867
	.end0:
1881
 
1868
 
1882
	send_code edi, END_BLOCK, [ltree]
1869
	send_code edi, END_BLOCK, [ltree]
1883
	ret
1870
	ret
1884
endp
1871
endp
1885
 
1872
 
1886
; ===========================================================================
1873
; ===========================================================================
1887
; Check if the data type is TEXT or BINARY, using the following algorithm:
1874
; Check if the data type is TEXT or BINARY, using the following algorithm:
1888
; - TEXT if the two conditions below are satisfied:
1875
; - TEXT if the two conditions below are satisfied:
1889
;    a) There are no non-portable control characters belonging to the
1876
;    a) There are no non-portable control characters belonging to the
1890
;       "black list" (0..6, 14..25, 28..31).
1877
;       "black list" (0..6, 14..25, 28..31).
1891
;    b) There is at least one printable character belonging to the
1878
;    b) There is at least one printable character belonging to the
1892
;       "white list" (9 {TAB}, 10 {LF}, 13 {CR}, 32..255).
1879
;       "white list" (9 {TAB}, 10 {LF}, 13 {CR}, 32..255).
1893
; - BINARY otherwise.
1880
; - BINARY otherwise.
1894
; - The following partially-portable control characters form a
1881
; - The following partially-portable control characters form a
1895
;   "gray list" that is ignored in this detection algorithm:
1882
;   "gray list" that is ignored in this detection algorithm:
1896
;   (7 {BEL}, 8 {BS}, 11 {VT}, 12 {FF}, 26 {SUB}, 27 {ESC}).
1883
;   (7 {BEL}, 8 {BS}, 11 {VT}, 12 {FF}, 26 {SUB}, 27 {ESC}).
1897
; IN assertion: the fields Freq of dyn_ltree are set.
1884
; IN assertion: the fields Freq of dyn_ltree are set.
1898
 
1885
 
1899
;int (s)
1886
;int (s)
1900
;    deflate_state* s
1887
;    deflate_state* s
1901
align 4
1888
align 4
1902
proc detect_data_type uses ebx ecx edi, s:dword
1889
proc detect_data_type uses ebx ecx edi, s:dword
1903
	; black_mask is the bit mask of black-listed bytes
1890
	; black_mask is the bit mask of black-listed bytes
1904
	; set bits 0..6, 14..25, and 28..31
1891
	; set bits 0..6, 14..25, and 28..31
1905
	; 0xf3ffc07f = binary 11110011111111111100000001111111
1892
	; 0xf3ffc07f = binary 11110011111111111100000001111111
1906
locals
1893
locals
1907
	black_mask dd 0xf3ffc07f
1894
	black_mask dd 0xf3ffc07f
1908
endl
1895
endl
1909
	mov edi,[s]
1896
	mov edi,[s]
1910
	zlib_debug 'detect_data_type'
1897
	zlib_debug 'detect_data_type'
1911
 
1898
 
1912
	; Check for non-textual ("black-listed") bytes.
1899
	; Check for non-textual ("black-listed") bytes.
1913
	xor ecx,ecx
1900
	xor ecx,ecx
1914
	mov ebx,edi
1901
	mov ebx,edi
1915
	add ebx,deflate_state.dyn_ltree+Freq
1902
	add ebx,deflate_state.dyn_ltree+Freq
1916
	.cycle0:
1903
	.cycle0:
1917
	cmp ecx,31
1904
	cmp ecx,31
1918
	jg .cycle0end ;for (..;..<=..;..,..)
1905
	jg .cycle0end ;for (..;..<=..;..,..)
1919
		bt dword[black_mask],0
1906
		bt dword[black_mask],0
1920
		jnc @f
1907
		jnc @f
1921
		cmp word[ebx],0
1908
		cmp word[ebx],0
1922
		je @f ;if (..&.. && ..!=0)
1909
		je @f ;if (..&.. && ..!=0)
1923
			mov eax,Z_BINARY
1910
			mov eax,Z_BINARY
1924
			jmp .end_f
1911
			jmp .end_f
1925
		@@:
1912
		@@:
1926
		shr dword[black_mask],1
1913
		shr dword[black_mask],1
1927
		add ebx,sizeof.ct_data
1914
		add ebx,sizeof.ct_data
1928
		inc ecx
1915
		inc ecx
1929
		jmp .cycle0
1916
		jmp .cycle0
1930
	.cycle0end:
1917
	.cycle0end:
1931
 
1918
 
1932
	; Check for textual ("white-listed") bytes.
1919
	; Check for textual ("white-listed") bytes.
1933
	mov ebx,edi
1920
	mov ebx,edi
1934
	add ebx,deflate_state.dyn_ltree+Freq+9*sizeof.ct_data
1921
	add ebx,deflate_state.dyn_ltree+Freq+9*sizeof.ct_data
1935
	cmp word[ebx],0
1922
	cmp word[ebx],0
1936
	jne @f
1923
	jne @f
1937
	add ebx,sizeof.ct_data
1924
	add ebx,sizeof.ct_data
1938
	cmp word[ebx],0
1925
	cmp word[ebx],0
1939
	jne @f
1926
	jne @f
1940
	add ebx,3*sizeof.ct_data
1927
	add ebx,3*sizeof.ct_data
1941
	cmp word[ebx],0
1928
	cmp word[ebx],0
1942
	je .end0
1929
	je .end0
1943
	@@: ;if (..!=0 || ..!=0 || ..!= 0)
1930
	@@: ;if (..!=0 || ..!=0 || ..!= 0)
1944
		mov eax,Z_TEXT
1931
		mov eax,Z_TEXT
1945
		jmp .end_f
1932
		jmp .end_f
1946
	.end0:
1933
	.end0:
1947
	mov ecx,32
1934
	mov ecx,32
1948
	mov ebx,edi
1935
	mov ebx,edi
1949
	add ebx,deflate_state.dyn_ltree+Freq+32*sizeof.ct_data
1936
	add ebx,deflate_state.dyn_ltree+Freq+32*sizeof.ct_data
1950
	.cycle1:
1937
	.cycle1:
1951
	cmp ecx,LITERALS
1938
	cmp ecx,LITERALS
1952
	jge .cycle1end ;for (..;..<..;..,..)
1939
	jge .cycle1end ;for (..;..<..;..,..)
1953
		cmp word[ebx],0
1940
		cmp word[ebx],0
1954
		je @f ;if (..!=0)
1941
		je @f ;if (..!=0)
1955
			mov eax,Z_TEXT
1942
			mov eax,Z_TEXT
1956
			jmp .end_f
1943
			jmp .end_f
1957
		@@:
1944
		@@:
1958
		add ebx,sizeof.ct_data
1945
		add ebx,sizeof.ct_data
1959
		inc ecx
1946
		inc ecx
1960
		jmp .cycle1
1947
		jmp .cycle1
1961
	.cycle1end:
1948
	.cycle1end:
1962
 
1949
 
1963
	; There are no "black-listed" or "white-listed" bytes:
1950
	; There are no "black-listed" or "white-listed" bytes:
1964
	; this stream either is empty or has tolerated ("gray-listed") bytes only.
1951
	; this stream either is empty or has tolerated ("gray-listed") bytes only.
1965
 
1952
 
1966
	mov eax,Z_BINARY
1953
	mov eax,Z_BINARY
1967
.end_f:
1954
.end_f:
1968
	ret
1955
	ret
1969
endp
1956
endp
1970
 
1957
 
1971
; ===========================================================================
1958
; ===========================================================================
1972
; Reverse the first len bits of a code, using straightforward code (a faster
1959
; Reverse the first len bits of a code, using straightforward code (a faster
1973
; method would use a table)
1960
; method would use a table)
1974
; IN assertion: 1 <= len <= 15
1961
; IN assertion: 1 <= len <= 15
1975
 
1962
 
1976
;unsigned (code, len)
1963
;unsigned (code, len)
1977
;    unsigned code ;the value to invert
1964
;    unsigned code ;the value to invert
1978
;    int len       ;its bit length
1965
;    int len       ;its bit length
1979
align 4
1966
align 4
1980
proc bi_reverse uses ebx, p1code:dword, len:dword
1967
proc bi_reverse uses ebx, p1code:dword, len:dword
1981
	zlib_debug 'bi_reverse'
1968
	zlib_debug 'bi_reverse'
1982
	xor eax,eax
1969
	xor eax,eax
1983
	@@: ;do
1970
	@@: ;do
1984
		mov ebx,[p1code]
1971
		mov ebx,[p1code]
1985
		and ebx,1
1972
		and ebx,1
1986
		or eax,ebx
1973
		or eax,ebx
1987
		shr dword[p1code],1
1974
		shr dword[p1code],1
1988
		shl eax,1
1975
		shl eax,1
1989
		dec dword[len]
1976
		dec dword[len]
1990
		cmp dword[len],0
1977
		cmp dword[len],0
1991
		jg @b ;while (..>..)
1978
		jg @b ;while (..>..)
1992
	shl eax,1
1979
	shr eax,1
1993
	ret
1980
	ret
1994
endp
1981
endp
1995
 
1982
 
1996
; ===========================================================================
1983
; ===========================================================================
1997
; Flush the bit buffer, keeping at most 7 bits in it.
1984
; Flush the bit buffer, keeping at most 7 bits in it.
1998
 
1985
 
1999
;void (s)
1986
;void (s)
2000
;    deflate_state* s
1987
;    deflate_state* s
2001
align 4
1988
align 4
2002
proc bi_flush uses eax ecx edi, s:dword
1989
proc bi_flush uses eax ecx edi, s:dword
2003
	mov edi,[s]
1990
	mov edi,[s]
2004
	cmp dword[edi+deflate_state.bi_valid],16
1991
	cmp dword[edi+deflate_state.bi_valid],16
2005
	jne @f ;if (..==..)
1992
	jne @f ;if (..==..)
2006
		mov cx,[edi+deflate_state.bi_buf]
1993
		mov cx,[edi+deflate_state.bi_buf]
2007
		put_short edi,cx
1994
		put_short edi,cx
2008
		mov word[edi+deflate_state.bi_buf],0
1995
		mov word[edi+deflate_state.bi_buf],0
2009
		mov dword[edi+deflate_state.bi_valid],0
1996
		mov dword[edi+deflate_state.bi_valid],0
2010
		jmp .end0
1997
		jmp .end0
2011
	@@: ;else if (..>=..)
1998
	@@: ;else if (..>=..)
2012
		cmp dword[edi+deflate_state.bi_valid],8
1999
		cmp dword[edi+deflate_state.bi_valid],8
2013
		jl .end0
2000
		jl .end0
2014
		mov cl,byte[edi+deflate_state.bi_buf]
2001
		mov cl,byte[edi+deflate_state.bi_buf]
2015
		put_byte edi,cl
2002
		put_byte edi,cl
2016
		shr word[edi+deflate_state.bi_buf],8
2003
		shr word[edi+deflate_state.bi_buf],8
2017
		sub dword[edi+deflate_state.bi_valid],8
2004
		sub dword[edi+deflate_state.bi_valid],8
2018
	.end0:
2005
	.end0:
2019
	ret
2006
	ret
2020
endp
2007
endp
2021
 
2008
 
2022
; ===========================================================================
2009
; ===========================================================================
2023
; Flush the bit buffer and align the output on a byte boundary
2010
; Flush the bit buffer and align the output on a byte boundary
2024
 
2011
 
2025
;void (s)
2012
;void (s)
2026
;    deflate_state* s
2013
;    deflate_state* s
2027
align 4
2014
align 4
2028
proc bi_windup uses eax ecx edi, s:dword
2015
proc bi_windup uses eax ecx edi, s:dword
2029
	mov edi,[s]
2016
	mov edi,[s]
2030
	cmp dword[edi+deflate_state.bi_valid],8
2017
	cmp dword[edi+deflate_state.bi_valid],8
2031
	jle @f ;if (..>..)
2018
	jle @f ;if (..>..)
2032
		mov cx,[edi+deflate_state.bi_buf]
2019
		mov cx,[edi+deflate_state.bi_buf]
2033
		put_short edi, cx
2020
		put_short edi, cx
2034
		jmp .end0
2021
		jmp .end0
2035
	@@: ;else if (..>0)
2022
	@@: ;else if (..>0)
2036
		cmp dword[edi+deflate_state.bi_valid],0
2023
		cmp dword[edi+deflate_state.bi_valid],0
2037
		jle .end0
2024
		jle .end0
2038
		mov cl,byte[edi+deflate_state.bi_buf]
2025
		mov cl,byte[edi+deflate_state.bi_buf]
2039
		put_byte edi, cl
2026
		put_byte edi, cl
2040
	.end0:
2027
	.end0:
2041
	mov word[edi+deflate_state.bi_buf],0
2028
	mov word[edi+deflate_state.bi_buf],0
2042
	mov dword[edi+deflate_state.bi_valid],0
2029
	mov dword[edi+deflate_state.bi_valid],0
2043
if DEBUG eq 1
2030
if DEBUG eq 1
2044
	mov eax,[edi+deflate_state.bits_sent]
2031
	mov eax,[edi+deflate_state.bits_sent]
2045
	add eax,7
2032
	add eax,7
2046
	and eax,not 7
2033
	and eax,not 7
2047
	mov [edi+deflate_state.bits_sent],eax
2034
	mov [edi+deflate_state.bits_sent],eax
2048
end if
2035
end if
2049
	ret
2036
	ret
2050
endp
2037
endp
2051
 
2038
 
2052
; ===========================================================================
2039
; ===========================================================================
2053
; Copy a stored block, storing first the length and its
2040
; Copy a stored block, storing first the length and its
2054
; one's complement if requested.
2041
; one's complement if requested.
2055
 
2042
 
2056
;void (s, buf, len, header)
2043
;void (s, buf, len, header)
2057
;    deflate_state* s
2044
;    deflate_state* s
2058
;    charf    *buf   ;the input data
2045
;    charf    *buf   ;the input data
2059
;    unsigned len    ;its length
2046
;    unsigned len    ;its length
2060
;    int      header ;true if block header must be written
2047
;    int      header ;true if block header must be written
2061
align 4
2048
align 4
2062
proc copy_block uses eax ebx ecx edi esi, s:dword, buf:dword, len:dword, p4header:dword
2049
proc copy_block uses eax ebx ecx edi esi, s:dword, buf:dword, len:dword, p4header:dword
2063
	mov edi,[s]
2050
	mov edi,[s]
2064
	stdcall bi_windup,edi ;align on byte boundary
2051
	stdcall bi_windup,edi ;align on byte boundary
2065
 
2052
 
2066
	cmp dword[p4header],0
2053
	cmp dword[p4header],0
2067
	je @f ;if (..)
2054
	je @f ;if (..)
2068
		mov ecx,[len]
2055
		mov ecx,[len]
2069
		put_short edi, cx
2056
		put_short edi, cx
2070
		not cx
2057
		not cx
2071
		put_short edi, cx
2058
		put_short edi, cx
2072
if DEBUG eq 1
2059
if DEBUG eq 1
2073
		add dword[edi+deflate_state.bits_sent],2*16
2060
		add dword[edi+deflate_state.bits_sent],2*16
2074
end if
2061
end if
2075
	@@:
2062
	@@:
2076
if DEBUG eq 1
2063
if DEBUG eq 1
2077
	mov ecx,[len]
2064
	mov ecx,[len]
2078
	shl ecx,3
2065
	shl ecx,3
2079
	add [edi+deflate_state.bits_sent],ecx
2066
	add [edi+deflate_state.bits_sent],ecx
2080
end if
2067
end if
2081
	mov ecx,[len]
2068
	mov ecx,[len]
2082
	mov esi,[buf]
2069
	mov esi,[buf]
2083
	@@: ;while (len--)
2070
	@@: ;while (len--)
2084
		lodsb
2071
		lodsb
2085
		mov bl,al
2072
		mov bl,al
2086
		put_byte edi, bl
2073
		put_byte edi, bl
2087
		loop @b
2074
		loop @b
2088
	ret
2075
	ret
2089
endp
2076
endp
2090
>
2077
>
2091
>
2078
>
2092
align>
2079
align>
2093
>
2080
>
2094
>
2081
>
2095
>
2082
>
2096
>
2083
>
2097
;>
2084
;>
2098
>
2085
>
2099
>
2086
>
2100
>
2087
>
2101
>
2088
>
2102
>
2089
>
2103
>
2090
>
2104
>
2091
>
2105
>
2092
>
2106
>
2093
>
2107
>
2094
>
2108
>
2095
>
2109
>
2096
>
2110
>
2097
>
2111
>
2098
>
2112
>
2099
>
2113
>
2100
>