1 // Copyright 2010 Google Inc.
2 //
3 // This code is licensed under the same terms as WebM:
4 // Software License Agreement: http://www.webmproject.org/license/software/
5 // Additional IP Rights Grant: http://www.webmproject.org/license/additional/
6 // -----------------------------------------------------------------------------
7 //
8 // Main decoding functions for WEBP images.
9 //
10 // Author: Skal (pascal.massimino@gmail.com)
11
12 #ifndef WEBP_WEBP_DECODE_H_
13 #define WEBP_WEBP_DECODE_H_
14
15 #include "./types.h"
16
17 #if defined(__cplusplus) || defined(c_plusplus)
18 extern "C" {
19 #endif
20
21 #define WEBP_DECODER_ABI_VERSION 0x0002
22
23 // Return the decoder's version number, packed in hexadecimal using 8bits for
24 // each of major/minor/revision. E.g: v2.5.7 is 0x020507.
25 WEBP_EXTERN(int) WebPGetDecoderVersion(void);
26
27 // Retrieve basic header information: width, height.
28 // This function will also validate the header and return 0 in
29 // case of formatting error.
30 // Pointers *width/*height can be passed NULL if deemed irrelevant.
31 WEBP_EXTERN(int) WebPGetInfo(const uint8_t* data, uint32_t data_size,
32 int* width, int* height);
33
34 // Decodes WEBP images pointed to by *data and returns RGB samples, along
35 // with the dimensions in *width and *height.
36 // The returned pointer should be deleted calling free().
37 // Returns NULL in case of error.
38 WEBP_EXTERN(uint8_t*) WebPDecodeRGB(const uint8_t* data, uint32_t data_size,
39 int* width, int* height);
40
41 // Same as WebPDecodeRGB, but returning RGBA data.
42 WEBP_EXTERN(uint8_t*) WebPDecodeRGBA(const uint8_t* data, uint32_t data_size,
43 int* width, int* height);
44
45 // Same as WebPDecodeRGBA, but returning ARGB data.
46 WEBP_EXTERN(uint8_t*) WebPDecodeARGB(const uint8_t* data, uint32_t data_size,
47 int* width, int* height);
48
49 // This variant decode to BGR instead of RGB.
50 WEBP_EXTERN(uint8_t*) WebPDecodeBGR(const uint8_t* data, uint32_t data_size,
51 int* width, int* height);
52 // This variant decodes to BGRA instead of RGBA.
53 WEBP_EXTERN(uint8_t*) WebPDecodeBGRA(const uint8_t* data, uint32_t data_size,
54 int* width, int* height);
55
56 // Decode WEBP images stored in *data in Y'UV format(*). The pointer returned is
57 // the Y samples buffer. Upon return, *u and *v will point to the U and V
58 // chroma data. These U and V buffers need NOT be free()'d, unlike the returned
59 // Y luma one. The dimension of the U and V planes are both (*width + 1) / 2
60 // and (*height + 1)/ 2.
61 // Upon return, the Y buffer has a stride returned as '*stride', while U and V
62 // have a common stride returned as '*uv_stride'.
63 // Return NULL in case of error.
64 // (*) Also named Y'CbCr. See: http://en.wikipedia.org/wiki/YCbCr
65 WEBP_EXTERN(uint8_t*) WebPDecodeYUV(const uint8_t* data, uint32_t data_size,
66 int* width, int* height,
67 uint8_t** u, uint8_t** v,
68 int* stride, int* uv_stride);
69
70 // These five functions are variants of the above ones, that decode the image
71 // directly into a pre-allocated buffer 'output_buffer'. The maximum storage
72 // available in this buffer is indicated by 'output_buffer_size'. If this
73 // storage is not sufficient (or an error occurred), NULL is returned.
74 // Otherwise, output_buffer is returned, for convenience.
75 // The parameter 'output_stride' specifies the distance (in bytes)
76 // between scanlines. Hence, output_buffer_size is expected to be at least
77 // output_stride x picture-height.
78 WEBP_EXTERN(uint8_t*) WebPDecodeRGBInto(
79 const uint8_t* data, uint32_t data_size,
80 uint8_t* output_buffer, int output_buffer_size, int output_stride);
81 WEBP_EXTERN(uint8_t*) WebPDecodeRGBAInto(
82 const uint8_t* data, uint32_t data_size,
83 uint8_t* output_buffer, int output_buffer_size, int output_stride);
84 WEBP_EXTERN(uint8_t*) WebPDecodeARGBInto(
85 const uint8_t* data, uint32_t data_size,
86 uint8_t* output_buffer, int output_buffer_size, int output_stride);
87 // BGR variants
88 WEBP_EXTERN(uint8_t*) WebPDecodeBGRInto(
89 const uint8_t* data, uint32_t data_size,
90 uint8_t* output_buffer, int output_buffer_size, int output_stride);
91 WEBP_EXTERN(uint8_t*) WebPDecodeBGRAInto(
92 const uint8_t* data, uint32_t data_size,
93 uint8_t* output_buffer, int output_buffer_size, int output_stride);
94
95 // WebPDecodeYUVInto() is a variant of WebPDecodeYUV() that operates directly
96 // into pre-allocated luma/chroma plane buffers. This function requires the
97 // strides to be passed: one for the luma plane and one for each of the
98 // chroma ones. The size of each plane buffer is passed as 'luma_size',
99 // 'u_size' and 'v_size' respectively.
100 // Pointer to the luma plane ('*luma') is returned or NULL if an error occurred
101 // during decoding (or because some buffers were found to be too small).
102 WEBP_EXTERN(uint8_t*) WebPDecodeYUVInto(
103 const uint8_t* data, uint32_t data_size,
104 uint8_t* luma, int luma_size, int luma_stride,
105 uint8_t* u, int u_size, int u_stride,
106 uint8_t* v, int v_size, int v_stride);
107
108 //-----------------------------------------------------------------------------
109 // Output colorspaces and buffer
110
111 // Colorspaces
112 typedef enum { MODE_RGB = 0, MODE_RGBA = 1,
113 MODE_BGR = 2, MODE_BGRA = 3,
114 MODE_ARGB = 4, MODE_RGBA_4444 = 5,
115 MODE_RGB_565 = 6,
116 // YUV modes must come after RGB ones.
117 MODE_YUV = 7, MODE_YUVA = 8, // yuv 4:2:0
118 MODE_LAST = 9
119 } WEBP_CSP_MODE;
120
121 // Generic structure for describing the sample buffer.
122 typedef struct { // view as RGBA
123 uint8_t* rgba; // pointer to RGBA samples
124 int stride; // stride in bytes from one scanline to the next.
125 int size; // total size of the *rgba buffer.
126 } WebPRGBABuffer;
127
128 typedef struct { // view as YUVA
129 uint8_t* y, *u, *v, *a; // pointer to luma, chroma U/V, alpha samples
130 int y_stride; // luma stride
131 int u_stride, v_stride; // chroma strides
132 int a_stride; // alpha stride
133 int y_size; // luma plane size
134 int u_size, v_size; // chroma planes size
135 int a_size; // alpha-plane size
136 } WebPYUVABuffer;
137
138 // Output buffer
139 typedef struct {
140 WEBP_CSP_MODE colorspace; // Colorspace.
141 int width, height; // Dimensions.
142 int is_external_memory; // If true, 'internal_memory' pointer is not used.
143 union {
144 WebPRGBABuffer RGBA;
145 WebPYUVABuffer YUVA;
146 } u; // Nameless union of buffer parameters.
147 uint8_t* private_memory; // Internally allocated memory (only when
148 // is_external_memory is false). Should not be used
149 // externally, but accessed via the buffer union.
150 } WebPDecBuffer;
151
152 // Internal, version-checked, entry point
153 WEBP_EXTERN(int) WebPInitDecBufferInternal(WebPDecBuffer* const, int);
154
155 // Initialize the structure as empty. Must be called before any other use.
156 // Returns false in case of version mismatch
WebPInitDecBuffer(WebPDecBuffer * const buffer)157 static inline int WebPInitDecBuffer(WebPDecBuffer* const buffer) {
158 return WebPInitDecBufferInternal(buffer, WEBP_DECODER_ABI_VERSION);
159 }
160
161 // Free any memory associated with the buffer. Must always be called last.
162 // Note: doesn't free the 'buffer' structure itself.
163 WEBP_EXTERN(void) WebPFreeDecBuffer(WebPDecBuffer* const buffer);
164
165 //-----------------------------------------------------------------------------
166 // Enumeration of the status codes
167
168 typedef enum {
169 VP8_STATUS_OK = 0,
170 VP8_STATUS_OUT_OF_MEMORY,
171 VP8_STATUS_INVALID_PARAM,
172 VP8_STATUS_BITSTREAM_ERROR,
173 VP8_STATUS_UNSUPPORTED_FEATURE,
174 VP8_STATUS_SUSPENDED,
175 VP8_STATUS_USER_ABORT,
176 VP8_STATUS_NOT_ENOUGH_DATA
177 } VP8StatusCode;
178
179 //-----------------------------------------------------------------------------
180 // Incremental decoding
181 //
182 // This API allows streamlined decoding of partial data.
183 // Picture can be incrementally decoded as data become available thanks to the
184 // WebPIDecoder object. This object can be left in a SUSPENDED state if the
185 // picture is only partially decoded, pending additional input.
186 // Code example:
187 //
188 // WebPIDecoder* const idec = WebPINew(mode);
189 // while (has_more_data) {
190 // // ... (get additional data)
191 // status = WebPIAppend(idec, new_data, new_data_size);
192 // if (status != VP8_STATUS_SUSPENDED ||
193 // break;
194 // }
195 //
196 // // The above call decodes the current available buffer.
197 // // Part of the image can now be refreshed by calling to
198 // // WebPIDecGetRGB()/WebPIDecGetYUV() etc.
199 // }
200 // WebPIDelete(idec);
201
202 typedef struct WebPIDecoder WebPIDecoder;
203
204 // Creates a new incremental decoder with the supplied buffer parameter.
205 // This output_buffer can be passed NULL, in which case a default output buffer
206 // is used (with MODE_RGB). Otherwise, an internal reference to 'output_buffer'
207 // is kept, which means that the lifespan of 'output_buffer' must be larger than
208 // that of the returned WebPIDecoder object.
209 // Returns NULL if the allocation failed.
210 WEBP_EXTERN(WebPIDecoder*) WebPINewDecoder(WebPDecBuffer* const output_buffer);
211
212 // Creates a WebPIDecoder object. Returns NULL in case of failure.
213 // TODO(skal): DEPRECATED. Prefer using WebPINewDecoder().
214 WEBP_EXTERN(WebPIDecoder*) WebPINew(WEBP_CSP_MODE mode);
215
216 // This function allocates and initializes an incremental-decoder object, which
217 // will output the r/g/b(/a) samples specified by 'mode' into a preallocated
218 // buffer 'output_buffer'. The size of this buffer is at least
219 // 'output_buffer_size' and the stride (distance in bytes between two scanlines)
220 // is specified by 'output_stride'. Returns NULL if the allocation failed.
221 WEBP_EXTERN(WebPIDecoder*) WebPINewRGB(
222 WEBP_CSP_MODE mode,
223 uint8_t* output_buffer, int output_buffer_size, int output_stride);
224
225 // This function allocates and initializes an incremental-decoder object, which
226 // will output the raw luma/chroma samples into a preallocated planes. The luma
227 // plane is specified by its pointer 'luma', its size 'luma_size' and its stride
228 // 'luma_stride'. Similarly, the chroma-u plane is specified by the 'u',
229 // 'u_size' and 'u_stride' parameters, and the chroma-v plane by 'v', 'v_size'
230 // and 'v_size'.
231 // Returns NULL if the allocation failed.
232 WEBP_EXTERN(WebPIDecoder*) WebPINewYUV(
233 uint8_t* luma, int luma_size, int luma_stride,
234 uint8_t* u, int u_size, int u_stride,
235 uint8_t* v, int v_size, int v_stride);
236
237 // Deletes the WebPIDecoder object and associated memory. Must always be called
238 // if WebPINew, WebPINewRGB or WebPINewYUV succeeded.
239 WEBP_EXTERN(void) WebPIDelete(WebPIDecoder* const idec);
240
241 // Copies and decodes the next available data. Returns VP8_STATUS_OK when
242 // the image is successfully decoded. Returns VP8_STATUS_SUSPENDED when more
243 // data is expected. Returns error in other cases.
244 WEBP_EXTERN(VP8StatusCode) WebPIAppend(
245 WebPIDecoder* const idec, const uint8_t* data, uint32_t data_size);
246
247 // A variant of the above function to be used when data buffer contains
248 // partial data from the beginning. In this case data buffer is not copied
249 // to the internal memory.
250 // Note that the value of the 'data' pointer can change between calls to
251 // WebPIUpdate, for instance when the data buffer is resized to fit larger data.
252 WEBP_EXTERN(VP8StatusCode) WebPIUpdate(
253 WebPIDecoder* const idec, const uint8_t* data, uint32_t data_size);
254
255 // Returns the r/g/b/(a) image decoded so far. Returns NULL if output params
256 // are not initialized yet. The r/g/b/(a) output type corresponds to the mode
257 // specified in WebPINew()/WebPINewRGB(). *last_y is the index of last decoded
258 // row in raster scan order. Some pointers (*last_y, *width etc.) can be NULL if
259 // corresponding information is not needed.
260 WEBP_EXTERN(uint8_t*) WebPIDecGetRGB(
261 const WebPIDecoder* const idec, int* last_y,
262 int* width, int* height, int* stride);
263
264 // Same as above function to get YUV image. Returns pointer to the luma plane
265 // or NULL in case of error.
266 WEBP_EXTERN(uint8_t*) WebPIDecGetYUV(
267 const WebPIDecoder* const idec, int* last_y,
268 uint8_t** u, uint8_t** v,
269 int* width, int* height, int* stride, int* uv_stride);
270
271 // Generic call to retrieve information about the displayable area.
272 // If non NULL, the left/right/width/height pointers are filled with the visible
273 // rectangular area so far.
274 // Returns NULL in case the incremental decoder object is in an invalid state.
275 // Otherwise returns the pointer to the internal representation. This structure
276 // is read-only, tied to WebPIDecoder's lifespan and should not be modified.
277 WEBP_EXTERN(const WebPDecBuffer*) WebPIDecodedArea(
278 const WebPIDecoder* const idec,
279 int* const left, int* const top,
280 int* const width, int* const height);
281
282 //-----------------------------------------------------------------------------
283 // Advanced decoding parametrization
284 //
285 // Code sample for using the advanced decoding API
286 /*
287 // A) Init a configuration object
288 WebPDecoderConfig config;
289 CHECK(WebPInitDecoderConfig(&config));
290
291 // B) optional: retrieve the bitstream's features.
292 CHECK(WebPGetFeatures(data, data_size, &config.input) == VP8_STATUS_OK);
293
294 // C) Adjust 'config', if needed
295 config.no_fancy = 1;
296 config.output.colorspace = MODE_BGRA;
297 // etc.
298
299 // Note that you can also make config.output point to an externally
300 // supplied memory buffer, provided it's big enough to store the decoded
301 // picture. Otherwise, config.output will just be used to allocate memory
302 // and store the decoded picture.
303
304 // D) Decode!
305 CHECK(WebPDecode(data, data_size, &config) == VP8_STATUS_OK);
306
307 // E) Decoded image is now in config.output (and config.output.u.RGBA)
308
309 // F) Reclaim memory allocated in config's object. It's safe to call
310 // this function even if the memory is external and wasn't allocated
311 // by WebPDecode().
312 WebPFreeDecBuffer(&config.output);
313 */
314
315 // Features gathered from the bitstream
316 typedef struct {
317 int width; // the original width, as read from the bitstream
318 int height; // the original height, as read from the bitstream
319 int has_alpha; // true if bitstream contains an alpha channel
320 int no_incremental_decoding; // if true, using incremental decoding is not
321 // recommended.
322 int rotate; // TODO(later)
323 int uv_sampling; // should be 0 for now. TODO(later)
324 int bitstream_version; // should be 0 for now. TODO(later)
325 } WebPBitstreamFeatures;
326
327 // Internal, version-checked, entry point
328 WEBP_EXTERN(VP8StatusCode) WebPGetFeaturesInternal(
329 const uint8_t*, uint32_t, WebPBitstreamFeatures* const, int);
330
331 // Retrieve features from the bitstream. The *features structure is filled
332 // with information gathered from the bitstream.
333 // Returns false in case of error or version mismatch.
334 // In case of error, features->bitstream_status will reflect the error code.
335 static inline
WebPGetFeatures(const uint8_t * data,uint32_t data_size,WebPBitstreamFeatures * const features)336 VP8StatusCode WebPGetFeatures(const uint8_t* data, uint32_t data_size,
337 WebPBitstreamFeatures* const features) {
338 return WebPGetFeaturesInternal(data, data_size, features,
339 WEBP_DECODER_ABI_VERSION);
340 }
341
342 // Decoding options
343 typedef struct {
344 int bypass_filtering; // if true, skip the in-loop filtering
345 int no_fancy_upsampling; // if true, use faster pointwise upsampler
346 int use_cropping; // if true, cropping is applied _first_
347 int crop_left, crop_top; // top-left position for cropping.
348 // Will be snapped to even values.
349 int crop_width, crop_height; // dimension of the cropping area
350 int use_scaling; // if true, scaling is applied _afterward_
351 int scaled_width, scaled_height; // final resolution
352 int force_rotation; // forced rotation (to be applied _last_)
353 int no_enhancement; // if true, discard enhancement layer
354 } WebPDecoderOptions;
355
356 // Main object storing the configuration for advanced decoding.
357 typedef struct {
358 WebPBitstreamFeatures input; // Immutable bitstream features (optional)
359 WebPDecBuffer output; // Output buffer (can point to external mem)
360 WebPDecoderOptions options; // Decoding options
361 } WebPDecoderConfig;
362
363 // Internal, version-checked, entry point
364 WEBP_EXTERN(int) WebPInitDecoderConfigInternal(WebPDecoderConfig* const, int);
365
366 // Initialize the configuration as empty. This function must always be
367 // called first, unless WebPGetFeatures() is to be called.
368 // Returns false in case of mismatched version.
WebPInitDecoderConfig(WebPDecoderConfig * const config)369 static inline int WebPInitDecoderConfig(WebPDecoderConfig* const config) {
370 return WebPInitDecoderConfigInternal(config, WEBP_DECODER_ABI_VERSION);
371 }
372
373 // Instantiate a new incremental decoder object with requested configuration.
374 // The bitstream can be passed using *data and data_size parameter,
375 // in which case the features will be parsed and stored into config->input.
376 // Otherwise, 'data' can be NULL and now parsing will occur.
377 // Note that 'config' can be NULL too, in which case a default configuration is
378 // used.
379 // The return WebPIDecoder object must always be deleted calling WebPIDelete().
380 // Returns NULL in case of error (and config->status will then reflect
381 // the error condition).
382 WEBP_EXTERN(WebPIDecoder*) WebPIDecode(const uint8_t* data, uint32_t data_size,
383 WebPDecoderConfig* const config);
384
385 // Non-incremental version. This version decodes the full data at once, taking
386 // 'config' into account. Return decoding status (VP8_STATUS_OK if decoding
387 // was successful).
388 WEBP_EXTERN(VP8StatusCode) WebPDecode(const uint8_t* data, uint32_t data_size,
389 WebPDecoderConfig* const config);
390
391 #if defined(__cplusplus) || defined(c_plusplus)
392 } // extern "C"
393 #endif
394
395 #endif /* WEBP_WEBP_DECODE_H_ */
396