#ifndef _COMPRESSAPI_H
#define _COMPRESSAPI_H

/* Windows Compression algorithms */

#include <windef.h>

#if (NTDDI_VERSION >= NTDDI_WIN8)

#if defined(WIN32_DEFAULT_LIBS)
#pragma comment(lib, "cabinet.lib")
#endif

#if __POCC__ >= 500
#pragma once
#endif

#ifdef __cplusplus
extern "C" {
#endif

DECLARE_HANDLE(COMPRESSOR_HANDLE);
typedef COMPRESSOR_HANDLE *PCOMPRESSOR_HANDLE;

typedef COMPRESSOR_HANDLE DECOMPRESSOR_HANDLE;
typedef COMPRESSOR_HANDLE *PDECOMPRESSOR_HANDLE;

#define COMPRESS_ALGORITHM_INVALID  0
#define COMPRESS_ALGORITHM_NULL  1
#define COMPRESS_ALGORITHM_MSZIP  2
#define COMPRESS_ALGORITHM_XPRESS  3
#define COMPRESS_ALGORITHM_XPRESS_HUFF  4
#define COMPRESS_ALGORITHM_LZMS  5
#define COMPRESS_ALGORITHM_MAX  6

#define COMPRESS_RAW  (1 << 29)

typedef PVOID (__cdecl *PFN_COMPRESS_ALLOCATE)(PVOID, SIZE_T);
typedef VOID (__cdecl *PFN_COMPRESS_FREE)(PVOID, PVOID);

typedef struct _COMPRESS_ALLOCATION_ROUTINES {
    PFN_COMPRESS_ALLOCATE Allocate;
    PFN_COMPRESS_FREE Free;
    PVOID UserContext;
}
COMPRESS_ALLOCATION_ROUTINES , *PCOMPRESS_ALLOCATION_ROUTINES;

typedef enum {
    COMPRESS_INFORMATION_CLASS_INVALID = 0,
    COMPRESS_INFORMATION_CLASS_BLOCK_SIZE,
    COMPRESS_INFORMATION_CLASS_LEVEL
} COMPRESS_INFORMATION_CLASS;

BOOL WINAPI CreateCompressor(DWORD, PCOMPRESS_ALLOCATION_ROUTINES, PCOMPRESSOR_HANDLE);
BOOL WINAPI SetCompressorInformation(COMPRESSOR_HANDLE, COMPRESS_INFORMATION_CLASS, PVOID, SIZE_T);
BOOL WINAPI QueryCompressorInformation(COMPRESSOR_HANDLE, COMPRESS_INFORMATION_CLASS, PVOID, SIZE_T);
BOOL WINAPI Compress(COMPRESSOR_HANDLE, PVOID, SIZE_T, PVOID, SIZE_T, PSIZE_T);
BOOL WINAPI ResetCompressor(COMPRESSOR_HANDLE);
BOOL WINAPI CloseCompressor(COMPRESSOR_HANDLE);

BOOL WINAPI CreateDecompressor(DWORD, PCOMPRESS_ALLOCATION_ROUTINES, PDECOMPRESSOR_HANDLE);
BOOL WINAPI SetDecompressorInformation(DECOMPRESSOR_HANDLE, COMPRESS_INFORMATION_CLASS, PVOID, SIZE_T);
BOOL WINAPI QueryDecompressorInformation(DECOMPRESSOR_HANDLE, COMPRESS_INFORMATION_CLASS, PVOID, SIZE_T);
BOOL WINAPI Decompress(DECOMPRESSOR_HANDLE, PVOID, SIZE_T, PVOID, SIZE_T, PSIZE_T);
BOOL WINAPI ResetDecompressor(DECOMPRESSOR_HANDLE);
BOOL WINAPI CloseDecompressor(DECOMPRESSOR_HANDLE);

#ifdef __cplusplus
}
#endif

#endif /* NTDDI_VERSION >= NTDDI_WIN8 */

#endif /* _COMPRESSAPI_H */
