diff --git a/uppsrc/Core/FilterStream.cpp b/uppsrc/Core/FilterStream.cpp index 47d50f330..e08cd9c34 100644 --- a/uppsrc/Core/FilterStream.cpp +++ b/uppsrc/Core/FilterStream.cpp @@ -100,6 +100,7 @@ void OutFilterStream::Init() wrlim = ~buffer + 4096; ptr = ~buffer; out = NULL; + count = 0; } OutFilterStream::~OutFilterStream() @@ -153,6 +154,7 @@ bool OutFilterStream::IsOpen() const void OutFilterStream::Out(const void *ptr, int size) { + count += size; out->Put(ptr, size); } diff --git a/uppsrc/Core/FilterStream.h b/uppsrc/Core/FilterStream.h index e207a218a..f2ae50c20 100644 --- a/uppsrc/Core/FilterStream.h +++ b/uppsrc/Core/FilterStream.h @@ -43,6 +43,7 @@ protected: virtual void _Put(const void *data, dword size); Buffer buffer; + int64 count; void FlushOut(); dword Avail() { return dword(4096 - (ptr - ~buffer)); } @@ -53,6 +54,8 @@ public: Callback2 Filter; Callback End; void Out(const void *ptr, int size); + + int64 GetCount() const { return count; } template void Set(Stream& out_, F& filter) { @@ -60,6 +63,7 @@ public: filter.WhenOut = callback(this, &OutFilterStream::Out); Filter = callback(&filter, &F::Put); End = callback(&filter, &F::End); + count = 0; } OutFilterStream(); diff --git a/uppsrc/Core/Stream.cpp b/uppsrc/Core/Stream.cpp index 8fdb6adda..a56475791 100644 --- a/uppsrc/Core/Stream.cpp +++ b/uppsrc/Core/Stream.cpp @@ -988,15 +988,15 @@ bool MemStream::IsOpen() const { return true; } -void MemStream::Create(void *data, int size) +void MemStream::Create(void *data, int64 size) { style = STRM_WRITE|STRM_READ|STRM_SEEK|STRM_LOADING; ptr = buffer = (byte *) data; - wrlim = rdlim = buffer + size; + wrlim = rdlim = buffer + (size_t)size; pos = 0; } -MemStream::MemStream(void *data, int size) { +MemStream::MemStream(void *data, int64 size) { Create(data, size); } @@ -1008,14 +1008,14 @@ MemStream::~MemStream() {} // ----------------------- Memory read streamer ------------------------- -void MemReadStream::Create(const void *data, int size) +void MemReadStream::Create(const void *data, int64 size) { MemStream::Create((void *)data, size); style = STRM_READ|STRM_SEEK|STRM_LOADING; wrlim = buffer; } -MemReadStream::MemReadStream(const void *data, int size) +MemReadStream::MemReadStream(const void *data, int64 size) { Create(data, size); } diff --git a/uppsrc/Core/Stream.h b/uppsrc/Core/Stream.h index ced8240a5..485de7e47 100644 --- a/uppsrc/Core/Stream.h +++ b/uppsrc/Core/Stream.h @@ -300,10 +300,10 @@ public: virtual bool IsOpen() const; public: - void Create(void *data, int size); + void Create(void *data, int64 size); MemStream(); - MemStream(void *data, int size); + MemStream(void *data, int64 size); #ifdef flagSO virtual ~MemStream(); #endif @@ -311,9 +311,9 @@ public: class MemReadStream : public MemStream { public: - void Create(const void *data, int size); + void Create(const void *data, int64 size); - MemReadStream(const void *data, int size); + MemReadStream(const void *data, int64 size); MemReadStream(); }; diff --git a/uppsrc/Core/src.tpp/OutFilterStream$en-us.tpp b/uppsrc/Core/src.tpp/OutFilterStream$en-us.tpp index d81bf0a12..e6b29ca0d 100644 --- a/uppsrc/Core/src.tpp/OutFilterStream$en-us.tpp +++ b/uppsrc/Core/src.tpp/OutFilterStream$en-us.tpp @@ -42,6 +42,11 @@ d]_`*, [@(0.0.255) int]>_[* Filter]&] st]_[@(0.0.255) void]_`*[*@3 ptr], [@(0.0.255) int]_[*@3 size])&] [s2;%% Method serving as filter output.&] [s3;%% &] +[s4; &] +[s5;:OutFilterStream`:`:GetCount`(`)const: [@(0.0.255) int64]_[* GetCount]()_[@(0.0.255) co +nst]&] +[s2;%% Returns a number of bytes written to the output.&] +[s3; &] [s4;%% &] [s5;:OutFilterStream`:`:Set`(Stream`&`,F`&`): [@(0.0.255) template]_<[@(0.0.255) class]_[*@4 F ]>_[@(0.0.255) void]_[* Set]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out`_], diff --git a/uppsrc/Core/src.tpp/Zlib$en-us.tpp b/uppsrc/Core/src.tpp/Zlib$en-us.tpp index b67ff78d9..f55bb8cca 100644 --- a/uppsrc/Core/src.tpp/Zlib$en-us.tpp +++ b/uppsrc/Core/src.tpp/Zlib$en-us.tpp @@ -128,79 +128,116 @@ in single zlib call.&] [s0; &] [ {{10000@(113.42.0) [s0;%% [*@7;4 Compression / decompression functions]]}}&] [s3; &] -[s5;:ZCompress`(Stream`&`,Stream`&`,Gate2``): [@(0.0.255) int]_[* ZCompress]([_^Stream^ S -tream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:ZCompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* ZCompress]( -[@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:ZCompress`(const String`&`,Gate2``): [_^String^ String]_[* ZCompress]([@(0.0.255) c -onst]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[@(0.0.255) int], -[@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZCompress`(Stream`&`,Stream`&`,int64`,Gate2``): [_^int64^ int64]_[* Z +Compress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 i +n], [_^int64^ int64]_[*@3 size], [_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 pr +ogress]_`=_[@(0.0.255) false])&] +[s5;:ZCompress`(Stream`&`,Stream`&`,Gate2``): [_^int64^ int64]_[* ZCompres +s]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZCompress`(const void`*`,int64`,Gate2``): [_^String^ String]_[* ZComp +ress]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [_^int64^ int64]_[*@3 len], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZCompress`(const String`&`,Gate2``): [_^String^ String]_[* ZCompress]( +[@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[_^int64^ int6 +4], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] [s2;%% Compresses raw data using zlib from input stream [%-*@3 in], memory [%-*@3 data][%- , ][%-*@3 len] or input string [%-*@3 s] to output stream [%-*@3 out] (in this case returns a number of bytes written -or negative integer to signal error) or into String return value. -[%-*@3 progress] can be used to track progress of operation, returning -true cancels it.&] +or negative integer to signal error) or into String return value +(returns IsVoid String on error). [%-*@3 progress] can be used +to track progress of operation, returning true cancels operation.&] [s3;%% &] [s4;%% &] -[s5;:ZDecompress`(Stream`&`,Stream`&`,Gate2``): [@(0.0.255) int]_[* ZDecompres -s]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:ZDecompress`(const String`&`,Gate2``): [_^String^ String]_[* ZDecompress]( -[@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[@(0.0.255) in -t], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:ZDecompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* ZDecompre -ss]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZDecompress`(Stream`&`,Stream`&`,int64`,Gate2``): [_^int64^ int64]_ +[* ZDecompress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `& +]_[*@3 in], [_^int64^ int64]_[*@3 size], [_^Gate2^ Gate2]<[_^int64^ int64], +[_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZDecompress`(Stream`&`,Stream`&`,Gate2``): [_^int64^ int64]_[* ZDecom +press]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in +], [_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false +])&] +[s5;:ZDecompress`(const void`*`,int64`,Gate2``): [_^String^ String]_[* ZDe +compress]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [_^int64^ int64]_[*@3 len], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:ZDecompress`(const String`&`,Gate2``): [_^String^ String]_[* ZDecompr +ess]([@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[_^int64^ i +nt64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] [s2;%% Decompresses raw data using zlib from input stream [%-*@3 in], memory [%-*@3 data][%- , ][%-*@3 len] or input string [%-*@3 s] to output stream [%-*@3 out] (in this case returns a number of bytes written -or negative integer to signal error) or into String return value. -[%-*@3 progress] can be used to track progress of operation, returning -true cancels it.&] +or negative integer to signal error) or into String return value +(returns IsVoid String on error). [%-*@3 progress] can be used +to track progress of operation, returning true cancels operation.&] [s3;%% &] [s4;%% &] -[s5;:GZCompress`(Stream`&`,Stream`&`,int`,Gate2``): [@(0.0.255) int]_[* GZComp -ress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], - [@(0.0.255) int]_[*@3 size], [_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progr -ess]_`=_[@(0.0.255) false])&] -[s5;:GZCompress`(Stream`&`,Stream`&`,Gate2``): [@(0.0.255) int]_[* GZCompress]( -[_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:GZCompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* GZCompress -]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:GZCompress`(const String`&`,Gate2``): [_^String^ String]_[* GZCompress]([@(0.0.255) c -onst]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[@(0.0.255) int], -[@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZCompress`(Stream`&`,Stream`&`,int64`,Gate2``): [_^int64^ int64]_[* G +ZCompress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 i +n], [_^int64^ int64]_[*@3 size], [_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 pr +ogress]_`=_[@(0.0.255) false])&] +[s5;:GZCompress`(Stream`&`,Stream`&`,Gate2``): [_^int64^ int64]_[* GZCompr +ess]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], + [_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false]) +&] +[s5;:GZCompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* GZComp +ress]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZCompress`(const String`&`,Gate2``): [_^String^ String]_[* GZCompres +s]([@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[_^int64^ i +nt64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] [s2;%% Compresses raw data into gzip file format from input stream [%-*@3 in], memory [%-*@3 data][%- , ][%-*@3 len] or input string [%-*@3 s] to output stream [%-*@3 out] (in this case returns a number of bytes written or negative integer to signal error) or into String -return value. [%-*@3 progress] can be used to track progress of -operation, returning true cancels it.&] +return value (returns IsVoid String on error). [%-*@3 progress] +can be used to track progress of operation, returning true cancels +operation.&] [s3;%% &] [s4;%% &] -[s5;:GZDecompress`(Stream`&`,Stream`&`,int`,Gate2``): [@(0.0.255) int]_[* GZDe -compress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 i -n], [@(0.0.255) int]_[*@3 size], [_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 pr -ogress]_`=_[@(0.0.255) false])&] -[s5;:GZDecompress`(Stream`&`,Stream`&`,Gate2``): [@(0.0.255) int]_[* GZDecompr -ess]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 in], - [_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false]) -&] -[s5;:GZDecompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* GZDecomp -ress]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], -[_^Gate2^ Gate2]<[@(0.0.255) int], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] -[s5;:GZDecompress`(const String`&`,Gate2``): [_^String^ String]_[* GZDecompres -s]([@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], [_^Gate2^ Gate2]<[@(0.0.255) i -nt], [@(0.0.255) int]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZDecompress`(Stream`&`,Stream`&`,int64`,Gate2``): [_^int64^ int64]_ +[* GZDecompress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `& +]_[*@3 in], [_^int64^ int64]_[*@3 size], [_^Gate2^ Gate2]<[_^int64^ int64], +[_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZDecompress`(Stream`&`,Stream`&`,Gate2``): [_^int64^ int64]_[* GZDec +ompress]([_^Stream^ Stream][@(0.0.255) `&]_[*@3 out], [_^Stream^ Stream][@(0.0.255) `&]_[*@3 i +n], [_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) fals +e])&] +[s5;:GZDecompress`(const void`*`,int`,Gate2``): [_^String^ String]_[* GZDe +compress]([@(0.0.255) const]_[@(0.0.255) void]_`*[*@3 data], [@(0.0.255) int]_[*@3 len], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZDecompress`(const String`&`,Gate2``): [_^String^ String]_[* GZDecom +press]([@(0.0.255) const]_[_^String^ String][@(0.0.255) `&]_[*@3 s], +[_^Gate2^ Gate2]<[_^int64^ int64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] [s2;%% Decompresses raw data into gzip file format from input stream [%-*@3 in], memory [%-*@3 data][%- , ][%-*@3 len] or input string [%-*@3 s] to output stream [%-*@3 out] (in this case returns a number of bytes written or negative integer to signal error) or into String -return value. [%-*@3 progress] can be used to track progress of -operation, returning true cancels it.&] +return value (returns IsVoid String on error). [%-*@3 progress] +can be used to track progress of operation, returning true cancels +operation.&] +[s3;%% &] +[s4;%% &] +[s5;:GZCompressFile`(const char`*`,const char`*`,Gate2``): [@(0.0.255) b +ool]_[* GZCompressFile]([@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 dstfile], +[@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 srcfile], [_^Gate2^ Gate2]<[_^int64^ int64], +[_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZCompressFile`(const char`*`,Gate2``): [@(0.0.255) bool]_[* GZCompre +ssFile]([@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 srcfile], [_^Gate2^ Gate2]<[_^int64^ in +t64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s2;%% Compresses file into gzip format. If [%-*@3 dstfile] is not +present, the name is created by appending .gz extension to [%-*@3 srcfile]. +Returns true on success.&] +[s3;%% &] +[s4;%% &] +[s5;:GZDecompressFile`(const char`*`,const char`*`,Gate2``): [@(0.0.255) b +ool]_[* GZDecompressFile]([@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 dstfile], +[@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 srcfile], [_^Gate2^ Gate2]<[_^int64^ int64], +[_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s5;:GZDecompressFile`(const char`*`,Gate2``): [@(0.0.255) bool]_[* GZDeco +mpressFile]([@(0.0.255) const]_[@(0.0.255) char]_`*[*@3 srcfile], [_^Gate2^ Gate2]<[_^int64^ i +nt64], [_^int64^ int64]>_[*@3 progress]_`=_[@(0.0.255) false])&] +[s2;%% Compresses file from gzip format. If [%-*@3 dstfile] is not +present, the name is created by removing .gz extension to [%-*@3 srcfile]. +If [%-*@3 srcfile] does not have .gz extension, function returns +false to signal error and does nothing. Returns true on success.&] [s0;%% ]] \ No newline at end of file diff --git a/uppsrc/Core/z.cpp b/uppsrc/Core/z.cpp index 095cc4123..ed276a4ba 100644 --- a/uppsrc/Core/z.cpp +++ b/uppsrc/Core/z.cpp @@ -304,196 +304,123 @@ Zlib::~Zlib() Free(); } -static int sZpress(Stream& out, Stream& in, int size, Gate2 progress, bool nohdr, dword *crc, - bool compress) -{ - const int BUF_SIZE = 65536; - Buffer input(BUF_SIZE), output(BUF_SIZE); - z_stream z; - z.zalloc = zalloc_new; - z.zfree = zfree_new; - z.opaque = 0; - if(compress ? deflateInit2(&z, Z_DEFAULT_COMPRESSION, Z_DEFLATED, - nohdr ? -MAX_WBITS : MAX_WBITS, DEF_MEM_LEVEL, Z_DEFAULT_STRATEGY) - : inflateInit2(&z, nohdr ? -MAX_WBITS : +MAX_WBITS) != Z_OK) { - out.SetError(); - return -1; +int64 CopyStream(Stream& dest, Stream& src, int64 count, Gate2 progress) { + int block = (int)min(count, 65536); + Buffer temp(block); + int loaded; + int64 done = 0; + int64 total = count; + while(count > 0 && (loaded = src.Get(temp, (int)min(count, block))) > 0) { + if(progress(done, total)) + return -1; + dest.Put(temp.operator const byte *(), loaded); + count -= loaded; + done += loaded; } - int code; - int flush; - int done = 0; - int outsz = 0; - if(crc) - *crc = crc32(0, NULL, 0); - do { - z.avail_in = in.Get(z.next_in = input, min(size - done, BUF_SIZE)); - if(progress(done += z.avail_in, size) || in.IsError()) - goto error; - if(!compress && z.avail_in == 0) - break; - flush = z.avail_in > 0 ? Z_NO_FLUSH : Z_FINISH; - if(crc && compress) - *crc = crc32(*crc, input, z.avail_in); - do { - z.avail_out = BUF_SIZE; - z.next_out = output; - code = (compress ? deflate : inflate)(&z, flush); - if(code == Z_STREAM_ERROR) - goto error; - int count = BUF_SIZE - z.avail_out; - if(crc && !compress) - *crc = crc32(*crc, output, count); - out.Put(output, count); - if(out.IsError()) - goto error; - outsz += count; - } - while(z.avail_out == 0); - } - while(compress ? flush != Z_FINISH : code != Z_STREAM_END); - if(!compress || code == Z_STREAM_END) { - (compress ? deflateEnd : inflateEnd)(&z); - return outsz; - } -error: - (compress ? deflateEnd : inflateEnd)(&z); - return -1; + return done; } -int ZCompress(Stream& out, Stream& in, int size, Gate2 progress, bool nohdr, dword *crc) +int64 zPress(Stream& out, Stream& in, int64 size, Gate2 progress, bool gzip, bool compress) { - return sZpress(out, in, size, progress, nohdr, crc, true); + Zlib zlib; + OutFilterStream outs(out, zlib); + zlib.GZip(gzip); + if(compress) + zlib.Compress(); + else + zlib.Decompress(); + return CopyStream(outs, in, size, progress) >= 0 && !out.IsError() ? outs.GetCount() : -1; } -int ZDecompress(Stream& out, Stream& in, int size, Gate2 progress, bool nohdr, dword *crc) +int64 ZCompress(Stream& out, Stream& in, int64 size, Gate2 progress) { - return sZpress(out, in, size, progress, nohdr, crc, false); + return zPress(out, in, size, progress, false, true); } -int ZCompress(Stream& out, Stream& in, Gate2 progress) +int64 ZDecompress(Stream& out, Stream& in, int64 size, Gate2 progress) { - return ZCompress(out, in, (int)in.GetLeft(), progress); + return zPress(out, in, size, progress, false, false); } -int ZDecompress(Stream& out, Stream& in, Gate2 progress) +int64 ZCompress(Stream& out, Stream& in, Gate2 progress) { - return ZDecompress(out, in, (int)in.GetLeft(), progress); + return ZCompress(out, in, in.GetLeft(), progress); } -String ZCompress(const void *data, int len, Gate2 progress) +int64 ZDecompress(Stream& out, Stream& in, Gate2 progress) +{ + return zPress(out, in, in.GetLeft(), progress, false, false); +} + +String ZCompress(const void *data, int64 len, Gate2 progress) { StringStream out; MemReadStream in(data, len); - ZCompress(out, in, progress); - return out; + return ZCompress(out, in, progress) < 0 ? String::GetVoid() : out; } -String ZDecompress(const void *data, int len, Gate2 progress) +String ZCompress(const String& s, Gate2 progress) +{ + return ZCompress(~s, s.GetLength(), progress); +} + +String ZDecompress(const void *data, int64 len, Gate2 progress) { StringStream out; MemReadStream in(data, len); - ZDecompress(out, in, progress); - return out; + return ZDecompress(out, in, progress) < 0 ? String::GetVoid() : out; } -String ZCompress(const String& s, Gate2 progress) +String ZDecompress(const String& s, Gate2 progress) { - return ZCompress(~s, s.GetCount(), progress); + return ZDecompress(~s, s.GetLength(), progress); } -String ZDecompress(const String& s, Gate2 progress) +int64 GZCompress(Stream& out, Stream& in, int64 size, Gate2 progress) { - return ZDecompress(~s, s.GetCount(), progress); + return zPress(out, in, size, progress, true, true); } -int GZCompress(Stream& out, Stream& in, int size, Gate2 progress) +int64 GZDecompress(Stream& out, Stream& in, int64 size, Gate2 progress) { - out.Put(sGZip_header, 10); - dword crc; - int sz = ZCompress(out, in, size, progress, true, &crc); - out.Put32le(crc); - out.Put32le(size); - return sz; + return zPress(out, in, size, progress, true, false); } -static int sSkipZ(Stream& stream) +int64 GZCompress(Stream& out, Stream& in, Gate2 progress) { - int q = 0; - while(stream.Get() > 0) - q++; - return q + 1; + return GZCompress(out, in, in.GetLeft(), progress); } -int GZDecompress(Stream& out, Stream& in, int size, Gate2 progress) -{ - byte buffer[10]; - if(!in.GetAll(buffer, 10) || buffer[0] != GZ_MAGIC1 || buffer[1] != GZ_MAGIC2) { - out.SetError(); - return -1; - } - int flags = buffer[3]; - if(buffer[2] != Z_DEFLATED || (flags & RESERVED) != 0) - return false; - size -= 10; - if(flags & EXTRA_FIELD) { - int len = in.Get16le(); - in.SeekCur(len); - size -= len; - } - if(flags & ORIG_NAME) - size -= sSkipZ(in); - if(flags & COMMENT) - size -= sSkipZ(in); - if(flags & HEAD_CRC) { - in.Get16le(); - size -= 2; - } - if(in.IsEof() || size < 0) { - out.SetError(); - return -1; - } - dword crc; - int sz = size < 8 ? -1 : ZDecompress(out, in, size - 8, progress, true, &crc); - return sz < 0 || in.Get32le() != (int)crc || in.Get32le() != sz ? -1 : sz; -} - -int GZCompress(Stream& out, Stream& in, Gate2 progress) -{ - return GZCompress(out, in, (int)in.GetLeft(), progress); -} - -int GZDecompress(Stream& out, Stream& in, Gate2 progress) -{ - return GZDecompress(out, in, (int)in.GetLeft(), progress); -} - -String GZCompress(const void *data, int len, Gate2 progress) +String GZCompress(const void *data, int len, Gate2 progress) { StringStream out; MemReadStream in(data, len); - GZCompress(out, in, progress); - return out; + return GZCompress(out, in, progress) < 0 ? String::GetVoid() : out; } -String GZDecompress(const void *data, int len, Gate2 progress) -{ - StringStream out; - MemReadStream in(data, len); - GZDecompress(out, in, progress); - return out; -} - -String GZCompress(const String& s, Gate2 progress) +String GZCompress(const String& s, Gate2 progress) { return GZCompress(~s, s.GetCount(), progress); } -String GZDecompress(const String& s, Gate2 progress) +int64 GZDecompress(Stream& out, Stream& in, Gate2 progress) +{ + return GZDecompress(out, in, in.GetLeft(), progress); +} + +String GZDecompress(const void *data, int len, Gate2 progress) +{ + StringStream out; + MemReadStream in(data, len); + return GZDecompress(out, in, progress) < 0 ? String::GetVoid() : out; +} + +String GZDecompress(const String& s, Gate2 progress) { return GZDecompress(~s, s.GetCount(), progress); } -bool GZCompressFile(const char *dstfile, const char *srcfile, Gate2 progress) +bool GZCompressFile(const char *dstfile, const char *srcfile, Gate2 progress) { FileIn in(srcfile); if(!in) @@ -507,13 +434,13 @@ bool GZCompressFile(const char *dstfile, const char *srcfile, Gate2 pr return !out.IsError(); } -bool GZCompressFile(const char *srcfile, Gate2 progress) +bool GZCompressFile(const char *srcfile, Gate2 progress) { String dstfile = String(srcfile) + ".gz"; return GZCompressFile(dstfile, srcfile, progress); } -bool GZDecompressFile(const char *dstfile, const char *srcfile, Gate2 progress) +bool GZDecompressFile(const char *dstfile, const char *srcfile, Gate2 progress) { FileIn in(srcfile); if(!in) @@ -527,7 +454,7 @@ bool GZDecompressFile(const char *dstfile, const char *srcfile, Gate2 return !out.IsError(); } -bool GZDecompressFile(const char *srcfile, Gate2 progress) +bool GZDecompressFile(const char *srcfile, Gate2 progress) { String dstfile = srcfile; if(!dstfile.EndsWith(".gz")) @@ -536,4 +463,14 @@ bool GZDecompressFile(const char *srcfile, Gate2 progress) return GZDecompressFile(dstfile, srcfile, progress); } +bool GateCv(int64 a, int64 b, Gate2 gate) +{ + return gate((int)a, (int)b); +} + +Gate2 AsGate64(Gate2 gate) +{ + return callback1(GateCv, gate); +} + END_UPP_NAMESPACE diff --git a/uppsrc/Core/z.h b/uppsrc/Core/z.h index 2998ae5b3..ad691b8e2 100644 --- a/uppsrc/Core/z.h +++ b/uppsrc/Core/z.h @@ -73,29 +73,51 @@ public: ~Zlib(); }; -int ZCompress(Stream& out, Stream& in, int size, Gate2 progress = false, bool nohdr = false, dword *crc = NULL); -int ZDecompress(Stream& out, Stream& in, int size, Gate2 progress = false, bool nohdr = false, dword *crc = NULL); -int ZCompress(Stream& out, Stream& in, Gate2 progress = false); -String ZCompress(const void *data, int len, Gate2 progress = false); -String ZCompress(const String& s, Gate2 progress = false); +int64 ZCompress(Stream& out, Stream& in, int64 size, Gate2 progress = false); +int64 ZCompress(Stream& out, Stream& in, Gate2 progress = false); +String ZCompress(const void *data, int64 len, Gate2 progress = false); +String ZCompress(const String& s, Gate2 progress = false); -int ZDecompress(Stream& out, Stream& in, Gate2 progress = false); -String ZDecompress(const String& s, Gate2 progress = false); -String ZDecompress(const void *data, int len, Gate2 progress = false); +int64 ZDecompress(Stream& out, Stream& in, int64 size, Gate2 progress = false); +int64 ZDecompress(Stream& out, Stream& in, Gate2 progress = false); +String ZDecompress(const void *data, int64 len, Gate2 progress = false); +String ZDecompress(const String& s, Gate2 progress = false); -int GZCompress(Stream& out, Stream& in, int size, Gate2 progress = false); -int GZCompress(Stream& out, Stream& in, Gate2 progress = false); -String GZCompress(const void *data, int len, Gate2 progress = false); -String GZCompress(const String& s, Gate2 progress = false); +int64 GZCompress(Stream& out, Stream& in, int64 size, Gate2 progress = false); +int64 GZCompress(Stream& out, Stream& in, Gate2 progress = false); +String GZCompress(const void *data, int len, Gate2 progress = false); +String GZCompress(const String& s, Gate2 progress = false); -bool GZCompressFile(const char *dstfile, const char *srcfile, Gate2 progress = false); -bool GZCompressFile(const char *srcfile, Gate2 progress = false); +int64 GZDecompress(Stream& out, Stream& in, int64 size, Gate2 progress = false); +int64 GZDecompress(Stream& out, Stream& in, Gate2 progress = false); +String GZDecompress(const void *data, int len, Gate2 progress = false); +String GZDecompress(const String& s, Gate2 progress = false); -int GZDecompress(Stream& out, Stream& in, int size, Gate2 progress = false); -int GZDecompress(Stream& out, Stream& in, Gate2 progress = false); -String GZDecompress(const void *data, int len, Gate2 progress = false); -String GZDecompress(const String& s, Gate2 progress = false); +bool GZCompressFile(const char *dstfile, const char *srcfile, Gate2 progress = false); +bool GZCompressFile(const char *srcfile, Gate2 progress = false); -bool GZDecompressFile(const char *dstfile, const char *srcfile, Gate2 progress = false); -bool GZDecompressFile(const char *srcfile, Gate2 progress = false); +bool GZDecompressFile(const char *dstfile, const char *srcfile, Gate2 progress = false); +bool GZDecompressFile(const char *srcfile, Gate2 progress = false); + +/// Backward compatibility: + +Gate2 AsGate64(Gate2 gate); + +inline int ZCompress(Stream& out, Stream& in, Gate2 progress) { return (int)ZCompress(out, in, AsGate64(progress)); } +inline String ZCompress(const void *data, int len, Gate2 progress) { return ZCompress(data, len, AsGate64(progress)); } +inline String ZCompress(const String& s, Gate2 progress) { return ZCompress(s, AsGate64(progress)); } + +inline int ZDecompress(Stream& out, Stream& in, Gate2 progress) { return (int)ZDecompress(out, in, AsGate64(progress)); } +inline String ZDecompress(const String& s, Gate2 progress) { return ZDecompress(s, AsGate64(progress)); } +inline String ZDecompress(const void *data, int len, Gate2 progress) { return ZDecompress(data, len, AsGate64(progress)); } + +inline int GZCompress(Stream& out, Stream& in, int size, Gate2 progress) { return (int)GZCompress(out, in, size, AsGate64(progress)); } +inline int GZCompress(Stream& out, Stream& in, Gate2 progress) { return (int)GZCompress(out, in, AsGate64(progress)); } +inline String GZCompress(const void *data, int len, Gate2 progress) { return GZCompress(data, len, AsGate64(progress)); } +inline String GZCompress(const String& s, Gate2 progress) { return GZCompress(s, AsGate64(progress)); } + +inline int GZDecompress(Stream& out, Stream& in, int size, Gate2 progress) { return (int)GZDecompress(out, in, size, AsGate64(progress)); } +inline int GZDecompress(Stream& out, Stream& in, Gate2 progress) { return (int)GZDecompress(out, in, AsGate64(progress)); } +inline String GZDecompress(const void *data, int len, Gate2 progress) { return GZDecompress(data, len, AsGate64(progress)); } +inline String GZDecompress(const String& s, Gate2 progress) { return GZDecompress(s, AsGate64(progress)); }