126 |
126 |
127 GZ_MAGIC_ID := #[ 16r1f 16r8b ] |
127 GZ_MAGIC_ID := #[ 16r1f 16r8b ] |
128 |
128 |
129 ! ! |
129 ! ! |
130 |
130 |
|
131 !ZipStream class methodsFor:'ZipInterface compatibility - compress/uncompress'! |
|
132 |
|
133 compress: aUncompressedByteArray into: aCompressedByteArray |
|
134 "" |
|
135 ^ self flatBytesIn: aUncompressedByteArray |
|
136 from: 1 |
|
137 to: (aUncompressedByteArray size) |
|
138 into: aCompressedByteArray |
|
139 doCompress: true. |
|
140 ! |
|
141 |
|
142 flatBytesIn:bytesIn from:start to:stop into:bytesOut doCompress:doCompress |
|
143 "compress or uncompress the bytesIn buffer into the bytesOut buffer; returns |
|
144 the un/compressed size; on error an exception is raised |
|
145 " |
|
146 |errorNr size| |
|
147 |
|
148 size := stop - start + 1. |
|
149 |
|
150 ( (start between:1 and:stop) |
|
151 and:[size > 0 |
|
152 and:[bytesIn size >= stop |
|
153 and:[bytesOut size > 0]]] |
|
154 ) ifFalse:[ |
|
155 ^ self error:'invalid argument size' |
|
156 ]. |
|
157 |
|
158 %{ |
|
159 char * __bytesIn = 0; |
|
160 uLong __countIn = 0; |
|
161 char * __bytesOut = 0; |
|
162 uLong __countOut = 0; |
|
163 |
|
164 if( (__isSmallInteger(start)) && (__isSmallInteger(stop)) && (__isSmallInteger(size)) ) |
|
165 { |
|
166 __countIn = __intVal( size ); |
|
167 |
|
168 if (__isBytes(bytesIn)) { |
|
169 __bytesIn = __ByteArrayInstPtr(bytesIn)->ba_element; |
|
170 } else { |
|
171 if (__isString(bytesIn)) { |
|
172 __bytesIn = __stringVal( bytesIn ); |
|
173 } |
|
174 } |
|
175 |
|
176 if (__isBytes(bytesOut)) { |
|
177 __bytesOut = __ByteArrayInstPtr(bytesOut)->ba_element; |
|
178 __countOut = __byteArraySize( bytesOut ); |
|
179 } else { |
|
180 if (__isString(bytesOut)) { |
|
181 __bytesOut = __stringVal( bytesOut ); |
|
182 __countOut = __stringSize( bytesOut ); |
|
183 } |
|
184 } |
|
185 } |
|
186 |
|
187 if( __bytesOut && __bytesIn ) |
|
188 { |
|
189 int __result = Z_OK; |
|
190 |
|
191 __bytesIn += (__intVal( start)) - 1; |
|
192 |
|
193 if( doCompress == true ) |
|
194 __result = compress ( (Byte *) __bytesOut, & __countOut, (Byte *) __bytesIn, __countIn ); |
|
195 else |
|
196 __result = uncompress( (Byte *) __bytesOut, & __countOut, (Byte *) __bytesIn, __countIn ); |
|
197 |
|
198 if( __result == Z_OK ) |
|
199 { RETURN(__MKSMALLINT(__countOut)); } |
|
200 |
|
201 errorNr = __MKSMALLINT( __result ); |
|
202 } |
|
203 %}. |
|
204 |
|
205 errorNr isNil ifTrue:[ ^ self error:'invalid arguments' ]. |
|
206 errorNr == 1 ifTrue:[ ^ self error:'stream at end' ]. |
|
207 errorNr == -3 ifTrue:[ ^ self error:'input data are corrupted' ]. |
|
208 errorNr == -4 ifTrue:[ ^ self error:'not enough memory' ]. |
|
209 errorNr == -5 ifTrue:[ ^ self error:'not enough memory in the output stream' ]. |
|
210 |
|
211 self error:('compressing error: ', errorNr printString). |
|
212 ! |
|
213 |
|
214 uncompress: aCompressedByteArray into: aUncompressedByteArray |
|
215 "" |
|
216 ^ self flatBytesIn: aCompressedByteArray |
|
217 from: 1 |
|
218 to: (aCompressedByteArray size) |
|
219 into: aUncompressedByteArray |
|
220 doCompress: false. |
|
221 ! ! |
|
222 |
|
223 !ZipStream class methodsFor:'ZipInterface compatibility - crc'! |
|
224 |
|
225 crc32BytesIn:bytesIn |
|
226 "compute crc with the bytes buf[1.. bytesIn size] |
|
227 and return the crc |
|
228 " |
|
229 ^ self crc32BytesIn:bytesIn from:1 |
|
230 ! |
|
231 |
|
232 crc32BytesIn:bytesIn crc:aCrc |
|
233 "Update a running crc with the bytes buf[1.. bytesIn size] |
|
234 and return the updated |
|
235 " |
|
236 ^ self crc32BytesIn:bytesIn from:1 crc:aCrc |
|
237 ! |
|
238 |
|
239 crc32BytesIn:bytesIn from:start |
|
240 "compute crc with the bytes buf[start.. bytesIn size] |
|
241 and return the crc |
|
242 " |
|
243 ^ self crc32BytesIn:bytesIn from:start to:(bytesIn size) |
|
244 ! |
|
245 |
|
246 crc32BytesIn:bytesIn from:start crc:aCrc |
|
247 "Update a running crc with the bytes buf[start.. bytesIn size] |
|
248 and return the updated |
|
249 " |
|
250 ^ self crc32BytesIn:bytesIn from:start to:(bytesIn size) crc:aCrc |
|
251 ! |
|
252 |
|
253 crc32BytesIn:bytesIn from:start to:stop |
|
254 "compute crc with the bytes buf[start.. stop] |
|
255 and return the crc |
|
256 " |
|
257 ^ self crc32BytesIn:bytesIn from:start to:stop crc:0 |
|
258 ! |
|
259 |
|
260 crc32BytesIn:bytesIn from:start to:stop crc:crc |
|
261 "Update a running crc with the bytes buf[start.. stop] |
|
262 and return the updated |
|
263 " |
|
264 |size| |
|
265 |
|
266 size := stop - start + 1. |
|
267 |
|
268 ( (start between:1 and:stop) |
|
269 and:[size > 0 |
|
270 and:[bytesIn size >= stop]] |
|
271 ) ifFalse:[ |
|
272 ^ self error:'invalid argument size' |
|
273 ]. |
|
274 %{ |
|
275 if( (__isInteger(crc)) && (__isSmallInteger(start)) && (__isSmallInteger(size)) ) |
|
276 { |
|
277 char * __bytes = 0; |
|
278 |
|
279 if (__isBytes(bytesIn)) { |
|
280 __bytes = __ByteArrayInstPtr(bytesIn)->ba_element; |
|
281 } else { |
|
282 if (__isString(bytesIn)) { |
|
283 __bytes = __stringVal( bytesIn ); |
|
284 } |
|
285 } |
|
286 |
|
287 if( __bytes ) |
|
288 { |
|
289 uLong __crc = __longIntVal( crc ); |
|
290 uInt __size = __intVal( size ); |
|
291 |
|
292 __bytes += (__intVal( start)) - 1; |
|
293 __crc = crc32(__crc, (Byte *) __bytes, __size ); |
|
294 |
|
295 RETURN( __MKUINT(__crc) ); |
|
296 } |
|
297 } |
|
298 %}. |
|
299 |
|
300 ^ self error:'invalid argument size' |
|
301 ! ! |
|
302 |
131 !ZipStream methodsFor:'low level'! |
303 !ZipStream methodsFor:'low level'! |
132 |
304 |
133 zclose |
305 zclose |
134 "low level close of the zip stream |
306 "low level close of the zip stream |
135 " |
307 " |
136 %{ |
308 %{ |
137 OBJ _zstreamObj = __INST( zstream ); |
309 OBJ _zstreamObj = __INST( zstream ); |
138 |
310 |
139 if( _zstreamObj != nil ) |
311 if( _zstreamObj != nil ) |
140 { |
312 { |
141 zstream_s * _zstream = (zstream_s *) __externalBytesAddress( _zstreamObj ); |
313 zstream_s * _zstream = (zstream_s *) __externalBytesAddress( _zstreamObj ); |
142 |
314 |
143 __INST(zstream) = nil; |
315 __INST(zstream) = nil; |
144 |
316 |
145 if( _zstream->stream.state != NULL ) |
317 if( _zstream->stream.state != NULL ) |
146 { |
318 { |
147 if( _zstream->op_mode == e_opmode_inflate ) |
319 if( _zstream->op_mode == e_opmode_inflate ) |
148 inflateEnd( & _zstream->stream ); |
320 inflateEnd( & _zstream->stream ); |
149 else |
321 else |
150 deflateEnd( & _zstream->stream ); |
322 deflateEnd( & _zstream->stream ); |
151 } |
323 } |
152 free( _zstream ); |
324 free( _zstream ); |
153 } |
325 } |
154 %}. |
326 %}. |
155 ! |
327 ! |
156 |
328 |
157 zdeflate |
329 zdeflate |
488 |
660 |
489 openWithMode:aMode on:aStream |
661 openWithMode:aMode on:aStream |
490 |
662 |
491 super openWithMode:aMode on:aStream. |
663 super openWithMode:aMode on:aStream. |
492 self isReadable ifTrue:[ |
664 self isReadable ifTrue:[ |
493 "Check for the gzip magic id" |
665 "Check for the gzip magic id" |
494 |flags| |
666 |flags| |
495 |
667 |
496 GZ_MAGIC_ID do:[:b| |
668 GZ_MAGIC_ID do:[:b| |
497 onStream nextByte ~~ b ifTrue:[ self zerror:'version error' ] |
669 onStream nextByte ~~ b ifTrue:[ self zerror:'version error' ] |
498 ]. |
670 ]. |
499 |
671 |
500 onStream nextByte ~~ Z_DEFLATED ifTrue:[ |
672 onStream nextByte ~~ Z_DEFLATED ifTrue:[ |
501 self zerror:'invalid method (not deflated)' |
673 self zerror:'invalid method (not deflated)' |
502 ]. |
674 ]. |
503 |
675 |
504 flags := onStream nextByte. |
676 flags := onStream nextByte. |
505 (flags bitAnd:HEAD_RESERVED) ~~ 0 ifTrue:[ |
677 (flags bitAnd:HEAD_RESERVED) ~~ 0 ifTrue:[ |
506 self zerror:'wrong data format' |
678 self zerror:'wrong data format' |
507 ]. |
679 ]. |
508 |
680 |
509 "discard time, xflags and OS code" |
681 "discard time, xflags and OS code" |
510 onStream skip:6. |
682 onStream skip:6. |
511 |
683 |
512 (flags bitAnd:HEAD_EXTRA_FIELD) ~~ 0 ifTrue:[|len| |
684 (flags bitAnd:HEAD_EXTRA_FIELD) ~~ 0 ifTrue:[|len| |
513 "skip the extra field" |
685 "skip the extra field" |
514 len := onStream nextByte + (onStream nextByte bitShift:8). |
686 len := onStream nextByte + (onStream nextByte bitShift:8). |
515 len timesRepeat:[ onStream nextByte ]. |
687 len timesRepeat:[ onStream nextByte ]. |
516 ]. |
688 ]. |
517 |
689 |
518 (flags bitAnd:HEAD_ORIG_NAME) ~~ 0 ifTrue:[|b| |
690 (flags bitAnd:HEAD_ORIG_NAME) ~~ 0 ifTrue:[|b| |
519 "skip the original file name" |
691 "skip the original file name" |
520 [ (b := onStream nextByte) ~~ 0 ] whileTrue. |
692 [ (b := onStream nextByte) ~~ 0 ] whileTrue. |
521 ]. |
693 ]. |
522 |
694 |
523 (flags bitAnd:HEAD_CRC) ~~ 0 ifTrue:[ |
695 (flags bitAnd:HEAD_CRC) ~~ 0 ifTrue:[ |
524 "skip the header crc" |
696 "skip the header crc" |
525 onStream skip:2. |
697 onStream skip:2. |
526 ]. |
698 ]. |
527 ] ifFalse:[ |
699 ] ifFalse:[ |
528 "write the gzip magic id |
700 "write the gzip magic id |
529 " |
701 " |
530 GZ_MAGIC_ID do:[:b| onStream nextPutByte:b ]. |
702 GZ_MAGIC_ID do:[:b| onStream nextPutByte:b ]. |
531 |
703 |
532 "write the method" |
704 "write the method" |
533 onStream nextPutByte:Z_DEFLATED. |
705 onStream nextPutByte:Z_DEFLATED. |
534 |
706 |
535 "write the flags" |
707 "write the flags" |
536 onStream nextPutByte:0. |
708 onStream nextPutByte:0. |
537 |
709 |
538 "write time" |
710 "write time" |
539 4 timesRepeat:[ onStream nextPutByte:0 ]. |
711 4 timesRepeat:[ onStream nextPutByte:0 ]. |
540 |
712 |
541 "write xflags" |
713 "write xflags" |
542 onStream nextPutByte:0. |
714 onStream nextPutByte:0. |
543 |
715 |
544 "write OS code" |
716 "write OS code" |
545 onStream nextPutByte:HEAD_OS_CODE. |
717 onStream nextPutByte:HEAD_OS_CODE. |
546 ]. |
718 ]. |
547 ! ! |
719 ! ! |
548 |
720 |
549 !ZipStream class methodsFor:'documentation'! |
721 !ZipStream class methodsFor:'documentation'! |
550 |
722 |
551 version |
723 version |
552 ^ '$Header: /cvs/stx/stx/libbasic2/ZipStream.st,v 1.21 2003-08-29 19:31:33 cg Exp $' |
724 ^ '$Header: /cvs/stx/stx/libbasic2/ZipStream.st,v 1.22 2004-03-23 11:52:44 ab Exp $' |
553 ! ! |
725 ! ! |
554 |
726 |
555 ZipStream initialize! |
727 ZipStream initialize! |