4
* $PostgreSQL: pgsql/src/include/utils/pg_lzcompress.h,v 1.10 2003-11-29 19:52:08 pgsql Exp $
6
* Definitions for the builtin LZ compressor
10
#ifndef _PG_LZCOMPRESS_H_
11
#define _PG_LZCOMPRESS_H_
17
* The information at the top of the compressed data.
18
* The varsize must be kept the same data type as the value
19
* in front of all variable size data types in PostgreSQL.
22
typedef struct PGLZ_Header
32
* Macro to compute the maximum buffer required for the
33
* compression output. It is larger than the input, because
34
* in the worst case, we cannot write out one single tag but
35
* need one control byte per 8 literal data bytes plus the
36
* EOF mark at the end.
39
#define PGLZ_MAX_OUTPUT(_dlen) ((_dlen) + (((_dlen) | 0x07) >> 3) \
40
+ sizeof(PGLZ_Header))
45
* Macro to determine the uncompressed data size contained
49
#define PGLZ_RAW_SIZE(_lzdata) (_lzdata->rawsize)
52
* PGLZ_IS_COMPRESSED -
54
* Macro to determine if the data itself is stored as raw
58
#define PGLZ_IS_COMPRESSED(_lzdata) (_lzdata->varsize != \
65
* Macro to get access to the plain compressed or uncompressed
66
* data. Useful if PGLZ_IS_COMPRESSED returns false.
69
#define PGLZ_RAW_DATA(_lzdata) (((char *)(_lzdata)) + \
75
* Some values that control the compression algorithm.
77
* min_input_size Minimum input data size to start compression.
79
* force_input_size Input data size at which compressed storage is
80
* forced even if the compression rate drops below
81
* min_comp_rate (but not below 0).
83
* min_comp_rate Minimum compression rate (0-99%), the output
84
* must be smaller than the input. If that isn't
85
* the case, the compressor will throw away its
86
* output and copy the original, uncompressed data
87
* to the output buffer.
89
* match_size_good The initial GOOD match size when starting history
90
* lookup. When looking up the history to find a
91
* match that could be expressed as a tag, the
92
* algorithm does not always walk back entirely.
93
* A good match fast is usually better than the
94
* best possible one very late. For each iteration
95
* in the lookup, this value is lowered so the
96
* longer the lookup takes, the smaller matches
97
* are considered good.
99
* match_size_drop The percentage, match_size_good is lowered
100
* at each history check. Allowed values are
101
* 0 (no change until end) to 100 (only check
102
* latest history entry at all).
105
typedef struct PGLZ_Strategy
107
int32 min_input_size;
108
int32 force_input_size;
110
int32 match_size_good;
111
int32 match_size_drop;
118
* Decompression state variable for byte-per-byte decompression
119
* using pglz_decomp_getchar() macro.
122
typedef struct PGLZ_DecompState
124
unsigned char *temp_buf;
125
unsigned char *cp_in;
126
unsigned char *cp_end;
127
unsigned char *cp_out;
128
unsigned char *cp_copy;
129
int (*next_char) (struct PGLZ_DecompState *dstate);
137
* The standard strategies
139
* PGLZ_strategy_default Starts compression only if input is
140
* at least 256 bytes large. Stores output
141
* uncompressed if compression does not
142
* gain at least 20% size reducture but
143
* input does not exceed 6K. Stops history
144
* lookup if at least a 128 byte long
145
* match has been found.
147
* This is the default strategy if none
148
* is given to pglz_compress().
150
* PGLZ_strategy_always Starts compression on any infinitely
151
* small input and does fallback to
152
* uncompressed storage only if output
153
* would be larger than input.
155
* PGLZ_strategy_never Force pglz_compress to act as a custom
156
* interface for memcpy(). Only useful
157
* for generic interfacing.
160
extern PGLZ_Strategy *PGLZ_strategy_default;
161
extern PGLZ_Strategy *PGLZ_strategy_always;
162
extern PGLZ_Strategy *PGLZ_strategy_never;
166
* pglz_decomp_getchar -
168
* Get next character (or EOF) from decompressor.
169
* The status variable must be initialized before and deinitialized
170
* after compression with the next two macros below.
173
#define pglz_decomp_getchar(_ds) \
174
((*((_ds)->next_char))((_ds)))
180
* Initialize a decomp state from a compressed input.
183
#define pglz_decomp_init(_ds,_lz) do { \
184
(_ds)->cp_in = ((unsigned char *)(_lz)) \
185
+ sizeof(PGLZ_Header); \
186
(_ds)->cp_end = (_ds)->cp_in + (_lz)->varsize \
187
- sizeof(PGLZ_Header); \
188
if (PGLZ_IS_COMPRESSED((_lz))) { \
189
(_ds)->temp_buf = (unsigned char *) \
190
palloc(PGLZ_RAW_SIZE((_lz))); \
191
(_ds)->cp_out = (_ds)->temp_buf; \
192
(_ds)->next_char = pglz_get_next_decomp_char_from_lzdata; \
194
(_ds)->ctrl_count = 0; \
196
(_ds)->temp_buf = NULL; \
197
(_ds)->next_char = pglz_get_next_decomp_char_from_plain; \
205
* Deallocate resources after decompression.
208
#define pglz_decomp_end(_ds) do { \
209
if ((_ds)->temp_buf != NULL) \
210
pfree((void *)((_ds)->temp_buf)); \
215
* Global function declarations
218
int pglz_compress(char *source, int32 slen, PGLZ_Header *dest,
219
PGLZ_Strategy *strategy);
220
int pglz_decompress(PGLZ_Header *source, char *dest);
224
* Functions used by pglz_decomp_getchar().
228
extern int pglz_get_next_decomp_char_from_lzdata(PGLZ_DecompState *dstate);
229
extern int pglz_get_next_decomp_char_from_plain(PGLZ_DecompState *dstate);
231
#endif /* _PG_LZCOMPRESS_H_ */