File: n_svc_zlib.sru
Size: 20495
Date: Tue, 22 Jan 2008 23:39:16 +0100
$PBExportHeader$n_svc_zlib.sru
$PBExportComments$zLib library
forward
global type n_svc_zlib from nonvisualobject
end type
end forward

global type n_svc_zlib from nonvisualobject
end type
global n_svc_zlib n_svc_zlib

type prototypes
Function Long compress (Ref blob Destination, Ref ulong DestLen, Ref blob Source, ulong SourceLen ) Library "zlib.dll"
Function Long compress2 (Ref blob Destination, Ref ulong DestLen, Ref blob Source, ulong SourceLen, int Level ) Library "zlib.dll"
Function Long uncompress ( Ref blob Destination, Ref ulong DestLen, Ref blob Sourse, ulong SourceLen ) Library "zlib.dll"
Function Long gzopen ( Ref string Path, Ref String Mode ) Library "zlib.dll"
Function long gzread ( long File, Ref blob Buffer, ulong BufferLen ) Library "zlib.dll"
Function long gzwrite ( long File, Ref blob Buffer, ulong BufferLen ) Library "zlib.dll"
Function long gzclose ( long File ) Library "zlib.dll"
Function string gzerror ( long File, Ref long ErrNum ) Library "zlib.dll"
Function long gzrewind ( long File ) Library "zlib.dll"
Function long gzeof ( long File ) Library "zlib.dll"
Function string zlibVersion() Library "zlib.dll"
FUNCTION ulong GetTempFileName(ref string lpszPath,ref string lpPrefixString,ulong wUnique,ref string lpTempFileName) LIBRARY "kernel32.dll" ALIAS FOR "GetTempFileNameA;Ansi"
FUNCTION ulong GetTempPath(ulong nBufferLength,ref string lpBuffer) LIBRARY "kernel32.dll" ALIAS FOR "GetTempPathA;Ansi"

end prototypes

type variables
// Constants as defined in ZLIB.H
////////////////////////////////
// Allowed flush values; see deflate()
Public Constant long Z_NO_FLUSH     = 0
Public Constant long Z_PARTIAL_FLUSH   = 1 // will be removed, use Z_SYNC_FLUSH instead
Public Constant long Z_SYNC_FLUSH      = 2
Public Constant long Z_FULL_FLUSH      = 3
Public Constant long Z_FINISH    = 4

// Return codes for the compression/decompression functions. Negative
// values are errors, positive values are used for special but normal events.
Public Constant long Z_OK        = 0
Public Constant long Z_STREAM_END      = 1
Public Constant long Z_NEED_DICT    = 2
Public Constant long Z_ERRNO     = -1
Public Constant long Z_STREAM_ERROR = -2
Public Constant long Z_DATA_ERROR      = -3
Public Constant long Z_MEM_ERROR    = -4
Public Constant long Z_BUF_ERROR    = -5
Public Constant long Z_VERSION_ERROR   = -6

// compression levels
Public Constant long Z_NO_COMPRESSION  = 0
Public Constant long Z_BEST_SPEED      = 1
Public Constant long Z_BEST_COMPRESSION   = 9
Public Constant long Z_DEFAULT_COMPRESSION = -1

// compression strategy; see deflateInit2()
Public Constant long Z_FILTERED     = 1
Public Constant long Z_HUFFMAN_ONLY = 2
Public Constant long Z_DEFAULT_STRATEGY   = 0

// Possible values of the data_type field
Public Constant long Z_BINARY    = 0
Public Constant long Z_ASCII        = 1
Public Constant long Z_UNKNOWN      = 2

// The deflate compression method (the only one supported in this version)
Public Constant long Z_DEFLATED     = 8
end variables

forward prototypes
public function string of_gzerror (long alfile, ref long alerrornumber)
public function long of_gzopen (string asfilename, string asmode)
public function long of_gzrewind (long alfile)
public function long of_gzwrite (long alfile, blob ablbuffer)
public function string of_zlibversion ()
public function long of_compress2 (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource, integer ailevel)
public function long of_gzclose (long alfile)
public function long of_gzread (long alfile, ref blob ablbuffer, unsignedlong aulbufferlength)
public function long of_gzeof (long alfile)
public function long of_compress (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource)
public function long of_compress (ref blob abldestination, blob ablsource)
public function long of_uncompress (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource)
public function long of_uncompress (ref blob abldestination, blob ablsource)
end prototypes

public function string of_gzerror (long alfile, ref long alerrornumber);//====================================================================
// Function - of_gzerror for nvo_zlib
//--------------------------------------------------------------------
// Description:Returns the error message for the last error which
//             occured on the given compressed file. 
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned by GZOPEN
// REF long alErrorNumber
//    zlib error number.
//--------------------------------------------------------------------
// Returns: (STRING) - Error message for the last error which occured.
//--------------------------------------------------------------------

RETURN gzerror( alFile, alErrorNumber )

end function

public function long of_gzopen (string asfilename, string asmode);//====================================================================
// Function - of_gzopen for nvo_zlib
//--------------------------------------------------------------------
// Description:Opens a gzip (.gz) file for reading or writing.
//             gzopen can be used to read a file which is NOT in gzip
//             format. In this case, gzread will directly read from
//             the file without decompression.
//--------------------------------------------------------------------
// Arguments:  
//
// string asfilename
//    Name of the filename (usually has a .gz extension)
// string asmode
//    "rb" = Read
//    "wb" = Write
//             You can also include the compression level:
//                e.g. "wb9" = Write + Level 9 (best) compression
//             You can also include the strategy:
//                e.g. "wb6f" = Write + Level 6 (default) compression + Filtered
//                e.g. "wb1h" = Write + Level 1 (fastest) compression + Huffman
//--------------------------------------------------------------------
// Returns: (LONG) - >0 = Success and returns the file handle
//                   NULL if the file could not be opened, or if there
//                   was insufficient memory to allocate the
//                   decompression state.
//--------------------------------------------------------------------

RETURN gzopen( asFileName, asMode )

end function

public function long of_gzrewind (long alfile);//====================================================================
// Function - of_gzrewind for nvo_zlib
//--------------------------------------------------------------------
// Description:Rewinds the given file. 
//
// NOTE: This function is only supported for reading.
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned by GZOPEN
//--------------------------------------------------------------------
// Returns: (LONG) - Z_OK
//--------------------------------------------------------------------

RETURN gzrewind( alFile )

end function

public function long of_gzwrite (long alfile, blob ablbuffer);//====================================================================
// Function - of_gzwrite for nvo_zlib
//--------------------------------------------------------------------
// Description:Writes the given number of UNCOMPRESSED bytes into
//             the compressed file.
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned by GZOPEN
// blob ablBuffer
//    Buffer containing the UNCOMPRESSED data.
//--------------------------------------------------------------------
// Returns: (LONG) - >0 Number of uncompressed bytes actually written
//                   0 = Error
//--------------------------------------------------------------------

RETURN gzwrite( alFile, ablBuffer, Len(ablBuffer) )

end function

public function string of_zlibversion ();//====================================================================
// Function - of_zlibversion for nvo_zlib
//--------------------------------------------------------------------
// Description:Returns the zlib version (currently 1.1.3)
//--------------------------------------------------------------------
// Returns: (STRING) - zlib version string
//--------------------------------------------------------------------

RETURN zlibVersion()

end function

public function long of_compress2 (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource, integer ailevel);//====================================================================
// Function - of_compress2 for nvo_zlib
//--------------------------------------------------------------------
// Description:Compress the source buffer into the destination
//             buffer. sourceLen is the byte length of the source
//             buffer and is automatically calculated using Len().
//             See notes below on initializing the destination buffer.
//             This is exactly the same as of_compress() except
//             you can now specify the compression level.
//--------------------------------------------------------------------
// Arguments:  
//
// REF blob abldestination
//    Destination buffer containing compressed data.
// REF unsignedlong auldestinationlength
//    Length of the compressed buffer.
// blob ablsource
//    Source (uncompressed) buffer.
// integer ailevel
//    The level parameter indicates the compression level.
//    It can be Z_DEFAULT_COMPRESSION (equates to a level of 6), 
//    or any number between 0 and 9, where
//    0 = Z_NO_COMPRESSION, 1 = Z_BEST_SPEED, 9 = Z_BEST_COMPRESSION
//--------------------------------------------------------------------
// Returns: (LONG) - Z_OK if success.
//                   Z_MEM_ERROR if there was not enough memory.
//                   Z_BUF_ERROR if there was not enough room in 
//                      the destination (output) buffer.
//--------------------------------------------------------------------

ulong lulSourceLen
long  llRC

lulSourceLen = Len( ablSource )

// As per zLib documentation:
// Upon entry, destLen is the total size of the destination buffer,
// which must be at least 0.1% larger than the sourcelen plus 12 bytes.
// Upon exit, destLen is the actual size of the compressed buffer.
//
// This actually makes the buffer 1% larger, better safe than sorry.
aulDestinationLength = (lulSourceLen * 101 / 100) + 12

// Initialize destination buffer before calling API function
ablDestination = Blob( Space(aulDestinationLength), EncodingANSI!)

llRC = compress2( ablDestination, aulDestinationLength, ablSource, lulSourceLen, aiLevel )

// Resize the destination buffer (blob) to the correct size
// The compression routine does not resize the allocated memory, so the
// destination buffer will still be the original size. Using the LEN() function
// will NOT return the same value as aulDestinationLength.
ablDestination = BlobMid( ablDestination, 1, aulDestinationLength )

RETURN llRC
end function

public function long of_gzclose (long alfile);//====================================================================
// Function - of_gzclose for nvo_zlib
//--------------------------------------------------------------------
// Description:Flushes all pending output if necessary, closes the
//             compressed file and deallocates all the compression
//             state.
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned by GZOPEN
//--------------------------------------------------------------------
// Returns: (LONG) - Returns the zlib error number (see GZERROR)
//--------------------------------------------------------------------

RETURN gzclose( alFile )

end function

public function long of_gzread (long alfile, ref blob ablbuffer, unsignedlong aulbufferlength);//====================================================================
// Function - of_gzread for nvo_zlib
//--------------------------------------------------------------------
// Description:Reads the given number of UNCOMPRESSED bytes from
//             the compressed file. If the input file is not in
//             gzip format, gzread copies the given number of bytes
//             into the buffer.
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned from GZOPEN
// blob ablBuffer
//    Buffer containing uncompressed data
// ulong aulBufferLength
//    Number of UNCOMPRESSED bytes to read from the file.
//--------------------------------------------------------------------
// Returns: (LONG) - >0 = The number of uncompressed bytes actually read.
//                    0 = End of file
//                   -1 = Error
//--------------------------------------------------------------------

// Allocate memory before calling API function
ablBuffer = Blob( Space(aulBufferLength) )

RETURN gzread( alFile, ablBuffer, aulBufferLength )

end function

public function long of_gzeof (long alfile);//====================================================================
// Function - of_gzeof for nvo_zlib
//--------------------------------------------------------------------
// Description:Returns 1 when EOF has previously been detected reading
//             the given input stream. Otherwise 0.
//--------------------------------------------------------------------
// Arguments:  
//
// long alFile
//    File handle returned by GZOPEN
//--------------------------------------------------------------------
// Returns: (LONG) - 1 = EOF
//                   0 = Not EOF
//--------------------------------------------------------------------

RETURN gzeof( alFile )

end function

public function long of_compress (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource);//====================================================================
// Function - of_compress for nvo_zlib
//--------------------------------------------------------------------
// Description:Compress the source buffer into the destination
//             buffer. sourceLen is the byte length of the source
//             buffer and is automatically calculated using Len().
//             See notes below on initializing the destination buffer.
//--------------------------------------------------------------------
// Arguments:  
//
// REF blob abldestination
//    Destination buffer containing compressed data.
// REF unsignedlong auldestinationlength
//    Length of the compressed buffer.
// blob ablsource
//    Source (uncompressed) buffer.
//--------------------------------------------------------------------
// Returns: (LONG) - Z_OK if success.
//                   Z_MEM_ERROR if there was not enough memory.
//                   Z_BUF_ERROR if there was not enough room in 
//                      the destination (output) buffer.
//--------------------------------------------------------------------

ulong lulSourceLen
long  llRC

// Calculate the length of the source (uncompressed) data.
lulSourceLen = Len( ablSource )

// As per zLib documentation:
// Upon entry, destLen is the total size of the destination buffer,
// which must be at least 0.1% larger than the sourcelen plus 12 bytes.
// Upon exit, destLen is the actual size of the compressed buffer.
//
// This actually makes the buffer 1% larger, better safe than sorry.
aulDestinationLength = (lulSourceLen * 101 / 100) + 12

// Initialize destination buffer before calling API function
ablDestination = Blob( Space(aulDestinationLength), EncodingANSI! )

// Perform in memory compression.
llRC = compress( ablDestination, aulDestinationLength, ablSource, lulSourceLen )

// Resize the destination buffer (blob) to the correct size
// The compression routine does not resize the allocated memory, so the
// destination buffer will still be the original size. Using the LEN() function
// will NOT return the same value as aulDestinationLength.
ablDestination = BlobMid( ablDestination, 1, aulDestinationLength )

RETURN llRC

end function

public function long of_compress (ref blob abldestination, blob ablsource);ulong llRC, ll


llRC = this.of_compress(abldestination, ll, ablsource)

ablDestination = BLOB("BUFFER=" + STRING(LEN(ablsource)) + ";", EncodingANSI!) + ablDestination

RETURN llRC
end function

public function long of_uncompress (ref blob abldestination, ref unsignedlong auldestinationlength, blob ablsource);//====================================================================
// Function - of_uncompress for nvo_zlib
//--------------------------------------------------------------------
// Description:Decompresses the source buffer into the destination
//             buffer. See the notes below for determining the 
//             size of the destination buffer.
//--------------------------------------------------------------------
// Arguments:  
//
// blob abldestination
//    Destination buffer containing uncompressed data
// unsignedlong auldestinationlength
//    Size of the destination buffer (length of uncompressed data)
// blob ablsource
//    Source buffer containing compressed data.
//--------------------------------------------------------------------
// Returns: (LONG) - Z_OK if success.
//                   Z_MEM_ERROR if there was not enough memory
//                   Z_BUF_ERROR if there is not enough memory in the
//                      output (destination) buffer.
//                   Z_DATA_ERROR if the input data is corrupted.
//--------------------------------------------------------------------

ulong lulSourceLen
long  llRC
string ls_src

lulSourceLen = Len( ablSource )

// As per zLib documentation:
//  Upon entry, destLen is the total size of the destination buffer, 
//  which must be large enough to hold the entire uncompressed data.
//  (The size of the uncompressed data must have been saved previously
//  by the compressor and transmitted to the decompressor by some
//  meachanism outside the scope of this compression library).
//  Upon exit, destLen is the actual size of the decompressed buffer.

// !!! THIS MEANS YOU MUST PASS IN THE DESTINATION LENGTH !!!

// Initialize destination buffer before calling API function
ablDestination = Blob( Space(aulDestinationLength), EncodingANSI!)

llRC = uncompress( ablDestination, aulDestinationLength, ablSource, lulSourceLen )

// Resize the destination buffer (blob) to the correct size
// The decompression routine does not resize the allocated memory, so the
// destination buffer will still be the original size. Using the LEN() function
// will NOT return the same value as aulDestinationLength.
ablDestination = BlobMid( ablDestination, 1, aulDestinationLength )

RETURN llRC

end function

public function long of_uncompress (ref blob abldestination, blob ablsource);//====================================================================
// Function - of_uncompress for nvo_zlib
//--------------------------------------------------------------------
// Description:Decompresses the source buffer into the destination
//             buffer. See the notes below for determining the 
//             size of the destination buffer.
//--------------------------------------------------------------------
// Arguments:  
//
// blob abldestination
//    Destination buffer containing uncompressed data
// unsignedlong auldestinationlength
//    Size of the destination buffer (length of uncompressed data)
// blob ablsource
//    Source buffer containing compressed data.
//--------------------------------------------------------------------
// Returns: (LONG) - Z_OK if success.
//                   Z_MEM_ERROR if there was not enough memory
//                   Z_BUF_ERROR if there is not enough memory in the
//                      output (destination) buffer.
//                   Z_DATA_ERROR if the input data is corrupted.
//--------------------------------------------------------------------

ulong lulSourceLen, auldestinationlength 
long  llRC
string ls_src
long ll_pos

ls_src = STRING(ablSource, EncodingANSI!)

ll_pos = POS(ls_src, ";")
//extract the length from the blob
IF ll_pos > 0 THEN
   ls_src = MID(ls_src, 1, ll_pos)
   ablSource = BLOBMID(ablSource, ll_pos + 1)
   ll_pos = POS(ls_src, "=")
   ls_src = MID(ls_src, ll_pos + 1)
   auldestinationlength = LONG(MID(ls_src, 1, LEN(ls_src) - 1))
ELSE
   RETURN -1
END IF

llRC = this.of_uncompress(abldestination, auldestinationlength, ablsource)

RETURN llRC

end function

on n_svc_zlib.create
call super::create
end on

on n_svc_zlib.destroy
call super::destroy
end on