stb_image.c revision 1.1.8.2 1 1.1.8.2 jruoho /* stbi-1.29 - public domain JPEG/PNG reader - http://nothings.org/stb_image.c
2 1.1.8.2 jruoho when you control the images you're loading
3 1.1.8.2 jruoho no warranty implied; use at your own risk
4 1.1.8.2 jruoho
5 1.1.8.2 jruoho QUICK NOTES:
6 1.1.8.2 jruoho Primarily of interest to game developers and other people who can
7 1.1.8.2 jruoho avoid problematic images and only need the trivial interface
8 1.1.8.2 jruoho
9 1.1.8.2 jruoho JPEG baseline (no JPEG progressive)
10 1.1.8.2 jruoho PNG 8-bit only
11 1.1.8.2 jruoho
12 1.1.8.2 jruoho TGA (not sure what subset, if a subset)
13 1.1.8.2 jruoho BMP non-1bpp, non-RLE
14 1.1.8.2 jruoho PSD (composited view only, no extra channels)
15 1.1.8.2 jruoho
16 1.1.8.2 jruoho GIF (*comp always reports as 4-channel)
17 1.1.8.2 jruoho HDR (radiance rgbE format)
18 1.1.8.2 jruoho PIC (Softimage PIC)
19 1.1.8.2 jruoho
20 1.1.8.2 jruoho - decoded from memory or through stdio FILE (define STBI_NO_STDIO to remove code)
21 1.1.8.2 jruoho - supports installable dequantizing-IDCT, YCbCr-to-RGB conversion (define STBI_SIMD)
22 1.1.8.2 jruoho
23 1.1.8.2 jruoho Latest revisions:
24 1.1.8.2 jruoho 1.29 (2010-08-16) various warning fixes from Aurelien Pocheville
25 1.1.8.2 jruoho 1.28 (2010-08-01) fix bug in GIF palette transparency (SpartanJ)
26 1.1.8.2 jruoho 1.27 (2010-08-01) cast-to-uint8 to fix warnings (Laurent Gomila)
27 1.1.8.2 jruoho allow trailing 0s at end of image data (Laurent Gomila)
28 1.1.8.2 jruoho 1.26 (2010-07-24) fix bug in file buffering for PNG reported by SpartanJ
29 1.1.8.2 jruoho 1.25 (2010-07-17) refix trans_data warning (Won Chun)
30 1.1.8.2 jruoho 1.24 (2010-07-12) perf improvements reading from files
31 1.1.8.2 jruoho minor perf improvements for jpeg
32 1.1.8.2 jruoho deprecated type-specific functions in hope of feedback
33 1.1.8.2 jruoho attempt to fix trans_data warning (Won Chun)
34 1.1.8.2 jruoho 1.23 fixed bug in iPhone support
35 1.1.8.2 jruoho 1.22 (2010-07-10) removed image *writing* support to stb_image_write.h
36 1.1.8.2 jruoho stbi_info support from Jetro Lauha
37 1.1.8.2 jruoho GIF support from Jean-Marc Lienher
38 1.1.8.2 jruoho iPhone PNG-extensions from James Brown
39 1.1.8.2 jruoho warning-fixes from Nicolas Schulz and Janez Zemva
40 1.1.8.2 jruoho 1.21 fix use of 'uint8' in header (reported by jon blow)
41 1.1.8.2 jruoho 1.20 added support for Softimage PIC, by Tom Seddon
42 1.1.8.2 jruoho
43 1.1.8.2 jruoho See end of file for full revision history.
44 1.1.8.2 jruoho
45 1.1.8.2 jruoho TODO:
46 1.1.8.2 jruoho stbi_info support for BMP,PSD,HDR,PIC
47 1.1.8.2 jruoho rewrite stbi_info and load_file variations to share file handling code
48 1.1.8.2 jruoho (current system allows individual functions to be called directly,
49 1.1.8.2 jruoho since each does all the work, but I doubt anyone uses this in practice)
50 1.1.8.2 jruoho
51 1.1.8.2 jruoho
52 1.1.8.2 jruoho ============================ Contributors =========================
53 1.1.8.2 jruoho
54 1.1.8.2 jruoho Image formats Optimizations & bugfixes
55 1.1.8.2 jruoho Sean Barrett (jpeg, png, bmp) Fabian "ryg" Giesen
56 1.1.8.2 jruoho Nicolas Schulz (hdr, psd)
57 1.1.8.2 jruoho Jonathan Dummer (tga) Bug fixes & warning fixes
58 1.1.8.2 jruoho Jean-Marc Lienher (gif) Marc LeBlanc
59 1.1.8.2 jruoho Tom Seddon (pic) Christpher Lloyd
60 1.1.8.2 jruoho Thatcher Ulrich (psd) Dave Moore
61 1.1.8.2 jruoho Won Chun
62 1.1.8.2 jruoho the Horde3D community
63 1.1.8.2 jruoho Extensions, features Janez Zemva
64 1.1.8.2 jruoho Jetro Lauha (stbi_info) Jonathan Blow
65 1.1.8.2 jruoho James "moose2000" Brown (iPhone PNG) Laurent Gomila
66 1.1.8.2 jruoho Aruelien Pocheville
67 1.1.8.2 jruoho
68 1.1.8.2 jruoho If your name should be here but isn't, let Sean know.
69 1.1.8.2 jruoho
70 1.1.8.2 jruoho */
71 1.1.8.2 jruoho
72 1.1.8.2 jruoho #ifdef _KERNEL
73 1.1.8.2 jruoho #include <dev/stbi/stbiconfig.h>
74 1.1.8.2 jruoho #endif
75 1.1.8.2 jruoho
76 1.1.8.2 jruoho #ifndef STBI_INCLUDE_STB_IMAGE_H
77 1.1.8.2 jruoho #define STBI_INCLUDE_STB_IMAGE_H
78 1.1.8.2 jruoho
79 1.1.8.2 jruoho // To get a header file for this, either cut and paste the header,
80 1.1.8.2 jruoho // or create stb_image.h, #define STBI_HEADER_FILE_ONLY, and
81 1.1.8.2 jruoho // then include stb_image.c from it.
82 1.1.8.2 jruoho
83 1.1.8.2 jruoho //// begin header file ////////////////////////////////////////////////////
84 1.1.8.2 jruoho //
85 1.1.8.2 jruoho // Limitations:
86 1.1.8.2 jruoho // - no jpeg progressive support
87 1.1.8.2 jruoho // - non-HDR formats support 8-bit samples only (jpeg, png)
88 1.1.8.2 jruoho // - no delayed line count (jpeg) -- IJG doesn't support either
89 1.1.8.2 jruoho // - no 1-bit BMP
90 1.1.8.2 jruoho // - GIF always returns *comp=4
91 1.1.8.2 jruoho //
92 1.1.8.2 jruoho // Basic usage (see HDR discussion below):
93 1.1.8.2 jruoho // int x,y,n;
94 1.1.8.2 jruoho // unsigned char *data = stbi_load(filename, &x, &y, &n, 0);
95 1.1.8.2 jruoho // // ... process data if not NULL ...
96 1.1.8.2 jruoho // // ... x = width, y = height, n = # 8-bit components per pixel ...
97 1.1.8.2 jruoho // // ... replace '0' with '1'..'4' to force that many components per pixel
98 1.1.8.2 jruoho // stbi_image_free(data)
99 1.1.8.2 jruoho //
100 1.1.8.2 jruoho // Standard parameters:
101 1.1.8.2 jruoho // int *x -- outputs image width in pixels
102 1.1.8.2 jruoho // int *y -- outputs image height in pixels
103 1.1.8.2 jruoho // int *comp -- outputs # of image components in image file
104 1.1.8.2 jruoho // int req_comp -- if non-zero, # of image components requested in result
105 1.1.8.2 jruoho //
106 1.1.8.2 jruoho // The return value from an image loader is an 'unsigned char *' which points
107 1.1.8.2 jruoho // to the pixel data. The pixel data consists of *y scanlines of *x pixels,
108 1.1.8.2 jruoho // with each pixel consisting of N interleaved 8-bit components; the first
109 1.1.8.2 jruoho // pixel pointed to is top-left-most in the image. There is no padding between
110 1.1.8.2 jruoho // image scanlines or between pixels, regardless of format. The number of
111 1.1.8.2 jruoho // components N is 'req_comp' if req_comp is non-zero, or *comp otherwise.
112 1.1.8.2 jruoho // If req_comp is non-zero, *comp has the number of components that _would_
113 1.1.8.2 jruoho // have been output otherwise. E.g. if you set req_comp to 4, you will always
114 1.1.8.2 jruoho // get RGBA output, but you can check *comp to easily see if it's opaque.
115 1.1.8.2 jruoho //
116 1.1.8.2 jruoho // An output image with N components has the following components interleaved
117 1.1.8.2 jruoho // in this order in each pixel:
118 1.1.8.2 jruoho //
119 1.1.8.2 jruoho // N=#comp components
120 1.1.8.2 jruoho // 1 grey
121 1.1.8.2 jruoho // 2 grey, alpha
122 1.1.8.2 jruoho // 3 red, green, blue
123 1.1.8.2 jruoho // 4 red, green, blue, alpha
124 1.1.8.2 jruoho //
125 1.1.8.2 jruoho // If image loading fails for any reason, the return value will be NULL,
126 1.1.8.2 jruoho // and *x, *y, *comp will be unchanged. The function stbi_failure_reason()
127 1.1.8.2 jruoho // can be queried for an extremely brief, end-user unfriendly explanation
128 1.1.8.2 jruoho // of why the load failed. Define STBI_NO_FAILURE_STRINGS to avoid
129 1.1.8.2 jruoho // compiling these strings at all, and STBI_FAILURE_USERMSG to get slightly
130 1.1.8.2 jruoho // more user-friendly ones.
131 1.1.8.2 jruoho //
132 1.1.8.2 jruoho // Paletted PNG, BMP, GIF, and PIC images are automatically depalettized.
133 1.1.8.2 jruoho //
134 1.1.8.2 jruoho // ===========================================================================
135 1.1.8.2 jruoho //
136 1.1.8.2 jruoho // iPhone PNG support:
137 1.1.8.2 jruoho //
138 1.1.8.2 jruoho // By default we convert iphone-formatted PNGs back to RGB; nominally they
139 1.1.8.2 jruoho // would silently load as BGR, except the existing code should have just
140 1.1.8.2 jruoho // failed on such iPhone PNGs. But you can disable this conversion by
141 1.1.8.2 jruoho // by calling stbi_convert_iphone_png_to_rgb(0), in which case
142 1.1.8.2 jruoho // you will always just get the native iphone "format" through.
143 1.1.8.2 jruoho //
144 1.1.8.2 jruoho // Call stbi_set_unpremultiply_on_load(1) as well to force a divide per
145 1.1.8.2 jruoho // pixel to remove any premultiplied alpha *only* if the image file explicitly
146 1.1.8.2 jruoho // says there's premultiplied data (currently only happens in iPhone images,
147 1.1.8.2 jruoho // and only if iPhone convert-to-rgb processing is on).
148 1.1.8.2 jruoho //
149 1.1.8.2 jruoho // ===========================================================================
150 1.1.8.2 jruoho //
151 1.1.8.2 jruoho // HDR image support (disable by defining STBI_NO_HDR)
152 1.1.8.2 jruoho //
153 1.1.8.2 jruoho // stb_image now supports loading HDR images in general, and currently
154 1.1.8.2 jruoho // the Radiance .HDR file format, although the support is provided
155 1.1.8.2 jruoho // generically. You can still load any file through the existing interface;
156 1.1.8.2 jruoho // if you attempt to load an HDR file, it will be automatically remapped to
157 1.1.8.2 jruoho // LDR, assuming gamma 2.2 and an arbitrary scale factor defaulting to 1;
158 1.1.8.2 jruoho // both of these constants can be reconfigured through this interface:
159 1.1.8.2 jruoho //
160 1.1.8.2 jruoho // stbi_hdr_to_ldr_gamma(2.2f);
161 1.1.8.2 jruoho // stbi_hdr_to_ldr_scale(1.0f);
162 1.1.8.2 jruoho //
163 1.1.8.2 jruoho // (note, do not use _inverse_ constants; stbi_image will invert them
164 1.1.8.2 jruoho // appropriately).
165 1.1.8.2 jruoho //
166 1.1.8.2 jruoho // Additionally, there is a new, parallel interface for loading files as
167 1.1.8.2 jruoho // (linear) floats to preserve the full dynamic range:
168 1.1.8.2 jruoho //
169 1.1.8.2 jruoho // float *data = stbi_loadf(filename, &x, &y, &n, 0);
170 1.1.8.2 jruoho //
171 1.1.8.2 jruoho // If you load LDR images through this interface, those images will
172 1.1.8.2 jruoho // be promoted to floating point values, run through the inverse of
173 1.1.8.2 jruoho // constants corresponding to the above:
174 1.1.8.2 jruoho //
175 1.1.8.2 jruoho // stbi_ldr_to_hdr_scale(1.0f);
176 1.1.8.2 jruoho // stbi_ldr_to_hdr_gamma(2.2f);
177 1.1.8.2 jruoho //
178 1.1.8.2 jruoho // Finally, given a filename (or an open file or memory block--see header
179 1.1.8.2 jruoho // file for details) containing image data, you can query for the "most
180 1.1.8.2 jruoho // appropriate" interface to use (that is, whether the image is HDR or
181 1.1.8.2 jruoho // not), using:
182 1.1.8.2 jruoho //
183 1.1.8.2 jruoho // stbi_is_hdr(char *filename);
184 1.1.8.2 jruoho
185 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
186 1.1.8.2 jruoho #include <stdio.h>
187 1.1.8.2 jruoho #endif
188 1.1.8.2 jruoho
189 1.1.8.2 jruoho #define STBI_VERSION 1
190 1.1.8.2 jruoho
191 1.1.8.2 jruoho enum
192 1.1.8.2 jruoho {
193 1.1.8.2 jruoho STBI_default = 0, // only used for req_comp
194 1.1.8.2 jruoho
195 1.1.8.2 jruoho STBI_grey = 1,
196 1.1.8.2 jruoho STBI_grey_alpha = 2,
197 1.1.8.2 jruoho STBI_rgb = 3,
198 1.1.8.2 jruoho STBI_rgb_alpha = 4
199 1.1.8.2 jruoho };
200 1.1.8.2 jruoho
201 1.1.8.2 jruoho typedef unsigned char stbi_uc;
202 1.1.8.2 jruoho
203 1.1.8.2 jruoho #ifdef __cplusplus
204 1.1.8.2 jruoho extern "C" {
205 1.1.8.2 jruoho #endif
206 1.1.8.2 jruoho
207 1.1.8.2 jruoho // PRIMARY API - works on images of any type
208 1.1.8.2 jruoho
209 1.1.8.2 jruoho // load image by filename, open file, or memory buffer
210 1.1.8.2 jruoho extern stbi_uc *stbi_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
211 1.1.8.2 jruoho
212 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
213 1.1.8.2 jruoho extern stbi_uc *stbi_load (char const *filename, int *x, int *y, int *comp, int req_comp);
214 1.1.8.2 jruoho extern stbi_uc *stbi_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
215 1.1.8.2 jruoho // for stbi_load_from_file, file pointer is left pointing immediately after image
216 1.1.8.2 jruoho #endif
217 1.1.8.2 jruoho
218 1.1.8.2 jruoho #ifndef STBI_NO_HDR
219 1.1.8.2 jruoho extern float *stbi_loadf_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
220 1.1.8.2 jruoho
221 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
222 1.1.8.2 jruoho extern float *stbi_loadf (char const *filename, int *x, int *y, int *comp, int req_comp);
223 1.1.8.2 jruoho extern float *stbi_loadf_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
224 1.1.8.2 jruoho #endif
225 1.1.8.2 jruoho
226 1.1.8.2 jruoho extern void stbi_hdr_to_ldr_gamma(float gamma);
227 1.1.8.2 jruoho extern void stbi_hdr_to_ldr_scale(float scale);
228 1.1.8.2 jruoho
229 1.1.8.2 jruoho extern void stbi_ldr_to_hdr_gamma(float gamma);
230 1.1.8.2 jruoho extern void stbi_ldr_to_hdr_scale(float scale);
231 1.1.8.2 jruoho #endif // STBI_NO_HDR
232 1.1.8.2 jruoho
233 1.1.8.2 jruoho // get a VERY brief reason for failure
234 1.1.8.2 jruoho // NOT THREADSAFE
235 1.1.8.2 jruoho extern const char *stbi_failure_reason (void);
236 1.1.8.2 jruoho
237 1.1.8.2 jruoho // free the loaded image -- this is just free()
238 1.1.8.2 jruoho extern void stbi_image_free (void *retval_from_stbi_load);
239 1.1.8.2 jruoho
240 1.1.8.2 jruoho // get image dimensions & components without fully decoding
241 1.1.8.2 jruoho extern int stbi_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp);
242 1.1.8.2 jruoho extern int stbi_is_hdr_from_memory(stbi_uc const *buffer, int len);
243 1.1.8.2 jruoho
244 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
245 1.1.8.2 jruoho extern int stbi_info (char const *filename, int *x, int *y, int *comp);
246 1.1.8.2 jruoho extern int stbi_info_from_file (FILE *f, int *x, int *y, int *comp);
247 1.1.8.2 jruoho
248 1.1.8.2 jruoho extern int stbi_is_hdr (char const *filename);
249 1.1.8.2 jruoho extern int stbi_is_hdr_from_file(FILE *f);
250 1.1.8.2 jruoho #endif
251 1.1.8.2 jruoho
252 1.1.8.2 jruoho // for image formats that explicitly notate that they have premultiplied alpha,
253 1.1.8.2 jruoho // we just return the colors as stored in the file. set this flag to force
254 1.1.8.2 jruoho // unpremultiplication. results are undefined if the unpremultiply overflow.
255 1.1.8.2 jruoho extern void stbi_set_unpremultiply_on_load(int flag_true_if_should_unpremultiply);
256 1.1.8.2 jruoho
257 1.1.8.2 jruoho // indicate whether we should process iphone images back to canonical format,
258 1.1.8.2 jruoho // or just pass them through "as-is"
259 1.1.8.2 jruoho extern void stbi_convert_iphone_png_to_rgb(int flag_true_if_should_convert);
260 1.1.8.2 jruoho
261 1.1.8.2 jruoho
262 1.1.8.2 jruoho // ZLIB client - used by PNG, available for other purposes
263 1.1.8.2 jruoho
264 1.1.8.2 jruoho extern char *stbi_zlib_decode_malloc_guesssize(const char *buffer, int len, int initial_size, int *outlen);
265 1.1.8.2 jruoho extern char *stbi_zlib_decode_malloc_guesssize_headerflag(const char *buffer, int len, int initial_size, int *outlen, int parse_header);
266 1.1.8.2 jruoho extern char *stbi_zlib_decode_malloc(const char *buffer, int len, int *outlen);
267 1.1.8.2 jruoho extern int stbi_zlib_decode_buffer(char *obuffer, int olen, const char *ibuffer, int ilen);
268 1.1.8.2 jruoho
269 1.1.8.2 jruoho extern char *stbi_zlib_decode_noheader_malloc(const char *buffer, int len, int *outlen);
270 1.1.8.2 jruoho extern int stbi_zlib_decode_noheader_buffer(char *obuffer, int olen, const char *ibuffer, int ilen);
271 1.1.8.2 jruoho
272 1.1.8.2 jruoho // define new loaders
273 1.1.8.2 jruoho typedef struct
274 1.1.8.2 jruoho {
275 1.1.8.2 jruoho int (*test_memory)(stbi_uc const *buffer, int len);
276 1.1.8.2 jruoho stbi_uc * (*load_from_memory)(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
277 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
278 1.1.8.2 jruoho int (*test_file)(FILE *f);
279 1.1.8.2 jruoho stbi_uc * (*load_from_file)(FILE *f, int *x, int *y, int *comp, int req_comp);
280 1.1.8.2 jruoho #endif
281 1.1.8.2 jruoho } stbi_loader;
282 1.1.8.2 jruoho
283 1.1.8.2 jruoho // register a loader by filling out the above structure (you must define ALL functions)
284 1.1.8.2 jruoho // returns 1 if added or already added, 0 if not added (too many loaders)
285 1.1.8.2 jruoho // NOT THREADSAFE
286 1.1.8.2 jruoho extern int stbi_register_loader(stbi_loader *loader);
287 1.1.8.2 jruoho
288 1.1.8.2 jruoho // define faster low-level operations (typically SIMD support)
289 1.1.8.2 jruoho #ifdef STBI_SIMD
290 1.1.8.2 jruoho typedef void (*stbi_idct_8x8)(stbi_uc *out, int out_stride, short data[64], unsigned short *dequantize);
291 1.1.8.2 jruoho // compute an integer IDCT on "input"
292 1.1.8.2 jruoho // input[x] = data[x] * dequantize[x]
293 1.1.8.2 jruoho // write results to 'out': 64 samples, each run of 8 spaced by 'out_stride'
294 1.1.8.2 jruoho // CLAMP results to 0..255
295 1.1.8.2 jruoho typedef void (*stbi_YCbCr_to_RGB_run)(stbi_uc *output, stbi_uc const *y, stbi_uc const *cb, stbi_uc const *cr, int count, int step);
296 1.1.8.2 jruoho // compute a conversion from YCbCr to RGB
297 1.1.8.2 jruoho // 'count' pixels
298 1.1.8.2 jruoho // write pixels to 'output'; each pixel is 'step' bytes (either 3 or 4; if 4, write '255' as 4th), order R,G,B
299 1.1.8.2 jruoho // y: Y input channel
300 1.1.8.2 jruoho // cb: Cb input channel; scale/biased to be 0..255
301 1.1.8.2 jruoho // cr: Cr input channel; scale/biased to be 0..255
302 1.1.8.2 jruoho
303 1.1.8.2 jruoho extern void stbi_install_idct(stbi_idct_8x8 func);
304 1.1.8.2 jruoho extern void stbi_install_YCbCr_to_RGB(stbi_YCbCr_to_RGB_run func);
305 1.1.8.2 jruoho #endif // STBI_SIMD
306 1.1.8.2 jruoho
307 1.1.8.2 jruoho
308 1.1.8.2 jruoho
309 1.1.8.2 jruoho
310 1.1.8.2 jruoho // TYPE-SPECIFIC ACCESS
311 1.1.8.2 jruoho
312 1.1.8.2 jruoho #ifdef STBI_TYPE_SPECIFIC_FUNCTIONS
313 1.1.8.2 jruoho
314 1.1.8.2 jruoho // is it a jpeg?
315 1.1.8.2 jruoho extern int stbi_jpeg_test_memory (stbi_uc const *buffer, int len);
316 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
317 1.1.8.2 jruoho extern int stbi_jpeg_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp);
318 1.1.8.2 jruoho
319 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
320 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load (char const *filename, int *x, int *y, int *comp, int req_comp);
321 1.1.8.2 jruoho extern int stbi_jpeg_test_file (FILE *f);
322 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
323 1.1.8.2 jruoho
324 1.1.8.2 jruoho extern int stbi_jpeg_info (char const *filename, int *x, int *y, int *comp);
325 1.1.8.2 jruoho extern int stbi_jpeg_info_from_file (FILE *f, int *x, int *y, int *comp);
326 1.1.8.2 jruoho #endif
327 1.1.8.2 jruoho
328 1.1.8.2 jruoho // is it a png?
329 1.1.8.2 jruoho extern int stbi_png_test_memory (stbi_uc const *buffer, int len);
330 1.1.8.2 jruoho extern stbi_uc *stbi_png_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
331 1.1.8.2 jruoho extern int stbi_png_info_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp);
332 1.1.8.2 jruoho
333 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
334 1.1.8.2 jruoho extern stbi_uc *stbi_png_load (char const *filename, int *x, int *y, int *comp, int req_comp);
335 1.1.8.2 jruoho extern int stbi_png_info (char const *filename, int *x, int *y, int *comp);
336 1.1.8.2 jruoho extern int stbi_png_test_file (FILE *f);
337 1.1.8.2 jruoho extern stbi_uc *stbi_png_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
338 1.1.8.2 jruoho extern int stbi_png_info_from_file (FILE *f, int *x, int *y, int *comp);
339 1.1.8.2 jruoho #endif
340 1.1.8.2 jruoho
341 1.1.8.2 jruoho // is it a bmp?
342 1.1.8.2 jruoho extern int stbi_bmp_test_memory (stbi_uc const *buffer, int len);
343 1.1.8.2 jruoho
344 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load (char const *filename, int *x, int *y, int *comp, int req_comp);
345 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
346 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
347 1.1.8.2 jruoho extern int stbi_bmp_test_file (FILE *f);
348 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
349 1.1.8.2 jruoho #endif
350 1.1.8.2 jruoho
351 1.1.8.2 jruoho // is it a tga?
352 1.1.8.2 jruoho extern int stbi_tga_test_memory (stbi_uc const *buffer, int len);
353 1.1.8.2 jruoho
354 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load (char const *filename, int *x, int *y, int *comp, int req_comp);
355 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
356 1.1.8.2 jruoho extern int stbi_tga_info_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp);
357 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
358 1.1.8.2 jruoho extern int stbi_tga_info_from_file (FILE *f, int *x, int *y, int *comp);
359 1.1.8.2 jruoho extern int stbi_tga_test_file (FILE *f);
360 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
361 1.1.8.2 jruoho #endif
362 1.1.8.2 jruoho
363 1.1.8.2 jruoho // is it a psd?
364 1.1.8.2 jruoho extern int stbi_psd_test_memory (stbi_uc const *buffer, int len);
365 1.1.8.2 jruoho
366 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load (char const *filename, int *x, int *y, int *comp, int req_comp);
367 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
368 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
369 1.1.8.2 jruoho extern int stbi_psd_test_file (FILE *f);
370 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
371 1.1.8.2 jruoho #endif
372 1.1.8.2 jruoho
373 1.1.8.2 jruoho // is it an hdr?
374 1.1.8.2 jruoho extern int stbi_hdr_test_memory (stbi_uc const *buffer, int len);
375 1.1.8.2 jruoho
376 1.1.8.2 jruoho extern float * stbi_hdr_load (char const *filename, int *x, int *y, int *comp, int req_comp);
377 1.1.8.2 jruoho extern float * stbi_hdr_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
378 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
379 1.1.8.2 jruoho extern int stbi_hdr_test_file (FILE *f);
380 1.1.8.2 jruoho extern float * stbi_hdr_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
381 1.1.8.2 jruoho #endif
382 1.1.8.2 jruoho
383 1.1.8.2 jruoho // is it a pic?
384 1.1.8.2 jruoho extern int stbi_pic_test_memory (stbi_uc const *buffer, int len);
385 1.1.8.2 jruoho
386 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load (char const *filename, int *x, int *y, int *comp, int req_comp);
387 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
388 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
389 1.1.8.2 jruoho extern int stbi_pic_test_file (FILE *f);
390 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
391 1.1.8.2 jruoho #endif
392 1.1.8.2 jruoho
393 1.1.8.2 jruoho // is it a gif?
394 1.1.8.2 jruoho extern int stbi_gif_test_memory (stbi_uc const *buffer, int len);
395 1.1.8.2 jruoho
396 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load (char const *filename, int *x, int *y, int *comp, int req_comp);
397 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
398 1.1.8.2 jruoho extern int stbi_gif_info_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp);
399 1.1.8.2 jruoho
400 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
401 1.1.8.2 jruoho extern int stbi_gif_test_file (FILE *f);
402 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
403 1.1.8.2 jruoho extern int stbi_gif_info (char const *filename, int *x, int *y, int *comp);
404 1.1.8.2 jruoho extern int stbi_gif_info_from_file (FILE *f, int *x, int *y, int *comp);
405 1.1.8.2 jruoho #endif
406 1.1.8.2 jruoho
407 1.1.8.2 jruoho #endif//STBI_TYPE_SPECIFIC_FUNCTIONS
408 1.1.8.2 jruoho
409 1.1.8.2 jruoho
410 1.1.8.2 jruoho
411 1.1.8.2 jruoho
412 1.1.8.2 jruoho #ifdef __cplusplus
413 1.1.8.2 jruoho }
414 1.1.8.2 jruoho #endif
415 1.1.8.2 jruoho
416 1.1.8.2 jruoho //
417 1.1.8.2 jruoho //
418 1.1.8.2 jruoho //// end header file /////////////////////////////////////////////////////
419 1.1.8.2 jruoho #endif // STBI_INCLUDE_STB_IMAGE_H
420 1.1.8.2 jruoho
421 1.1.8.2 jruoho #ifndef STBI_HEADER_FILE_ONLY
422 1.1.8.2 jruoho
423 1.1.8.2 jruoho #ifndef STBI_NO_HDR
424 1.1.8.2 jruoho #include <math.h> // ldexp
425 1.1.8.2 jruoho #include <string.h> // strcmp
426 1.1.8.2 jruoho #endif
427 1.1.8.2 jruoho
428 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
429 1.1.8.2 jruoho #include <stdio.h>
430 1.1.8.2 jruoho #endif
431 1.1.8.2 jruoho #ifdef _KERNEL
432 1.1.8.2 jruoho #include <sys/cdefs.h>
433 1.1.8.2 jruoho __KERNEL_RCSID(0, "$NetBSD: stb_image.c,v 1.1.8.2 2011/06/06 09:08:39 jruoho Exp $");
434 1.1.8.2 jruoho #include <sys/param.h>
435 1.1.8.2 jruoho #include <sys/systm.h>
436 1.1.8.2 jruoho #include <sys/kernel.h>
437 1.1.8.2 jruoho #include <sys/types.h>
438 1.1.8.2 jruoho #include <sys/malloc.h>
439 1.1.8.2 jruoho #else
440 1.1.8.2 jruoho #include <stdlib.h>
441 1.1.8.2 jruoho #include <memory.h>
442 1.1.8.2 jruoho #include <assert.h>
443 1.1.8.2 jruoho #include <stdarg.h>
444 1.1.8.2 jruoho #endif
445 1.1.8.2 jruoho
446 1.1.8.2 jruoho #ifdef _KERNEL
447 1.1.8.2 jruoho #define MALLOC(size) malloc((size), M_TEMP, M_WAITOK)
448 1.1.8.2 jruoho #define REALLOC(ptr, size) realloc((ptr), (size), M_TEMP, M_WAITOK)
449 1.1.8.2 jruoho #define FREE(ptr) free((ptr), M_TEMP)
450 1.1.8.2 jruoho #else
451 1.1.8.2 jruoho #define MALLOC(size) malloc((size))
452 1.1.8.2 jruoho #define REALLOC(ptr, size) realloc((ptr), (size))
453 1.1.8.2 jruoho #define FREE(ptr) free((ptr))
454 1.1.8.2 jruoho #endif
455 1.1.8.2 jruoho
456 1.1.8.2 jruoho #ifndef _MSC_VER
457 1.1.8.2 jruoho #ifdef __cplusplus
458 1.1.8.2 jruoho #define __forceinline inline
459 1.1.8.2 jruoho #else
460 1.1.8.2 jruoho #define __forceinline
461 1.1.8.2 jruoho #endif
462 1.1.8.2 jruoho #endif
463 1.1.8.2 jruoho
464 1.1.8.2 jruoho
465 1.1.8.2 jruoho // implementation:
466 1.1.8.2 jruoho typedef unsigned char uint8;
467 1.1.8.2 jruoho typedef unsigned short uint16;
468 1.1.8.2 jruoho typedef signed short int16;
469 1.1.8.2 jruoho typedef unsigned int uint32;
470 1.1.8.2 jruoho typedef signed int int32;
471 1.1.8.2 jruoho #ifndef __NetBSD__
472 1.1.8.2 jruoho typedef unsigned int uint;
473 1.1.8.2 jruoho #endif
474 1.1.8.2 jruoho
475 1.1.8.2 jruoho // should produce compiler error if size is wrong
476 1.1.8.2 jruoho typedef unsigned char validate_uint32[sizeof(uint32)==4 ? 1 : -1];
477 1.1.8.2 jruoho
478 1.1.8.2 jruoho #if defined(STBI_NO_STDIO) && !defined(STBI_NO_WRITE)
479 1.1.8.2 jruoho #define STBI_NO_WRITE
480 1.1.8.2 jruoho #endif
481 1.1.8.2 jruoho
482 1.1.8.2 jruoho #define STBI_NOTUSED(v) v=v
483 1.1.8.2 jruoho
484 1.1.8.2 jruoho #ifdef _MSC_VER
485 1.1.8.2 jruoho #define STBI_HAS_LRTOL
486 1.1.8.2 jruoho #endif
487 1.1.8.2 jruoho
488 1.1.8.2 jruoho #ifdef STBI_HAS_LRTOL
489 1.1.8.2 jruoho #define stbi_lrot(x,y) _lrotl(x,y)
490 1.1.8.2 jruoho #else
491 1.1.8.2 jruoho #define stbi_lrot(x,y) (((x) << (y)) | ((x) >> (32 - (y))))
492 1.1.8.2 jruoho #endif
493 1.1.8.2 jruoho
494 1.1.8.2 jruoho //////////////////////////////////////////////////////////////////////////////
495 1.1.8.2 jruoho //
496 1.1.8.2 jruoho // Generic API that works on all image types
497 1.1.8.2 jruoho //
498 1.1.8.2 jruoho
499 1.1.8.2 jruoho // deprecated functions
500 1.1.8.2 jruoho
501 1.1.8.2 jruoho // is it a jpeg?
502 1.1.8.2 jruoho extern int stbi_jpeg_test_memory (stbi_uc const *buffer, int len);
503 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
504 1.1.8.2 jruoho extern int stbi_jpeg_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp);
505 1.1.8.2 jruoho
506 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
507 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load (char const *filename, int *x, int *y, int *comp, int req_comp);
508 1.1.8.2 jruoho extern int stbi_jpeg_test_file (FILE *f);
509 1.1.8.2 jruoho extern stbi_uc *stbi_jpeg_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
510 1.1.8.2 jruoho
511 1.1.8.2 jruoho extern int stbi_jpeg_info (char const *filename, int *x, int *y, int *comp);
512 1.1.8.2 jruoho extern int stbi_jpeg_info_from_file (FILE *f, int *x, int *y, int *comp);
513 1.1.8.2 jruoho #endif
514 1.1.8.2 jruoho
515 1.1.8.2 jruoho // is it a png?
516 1.1.8.2 jruoho extern int stbi_png_test_memory (stbi_uc const *buffer, int len);
517 1.1.8.2 jruoho extern stbi_uc *stbi_png_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
518 1.1.8.2 jruoho extern int stbi_png_info_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp);
519 1.1.8.2 jruoho
520 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
521 1.1.8.2 jruoho extern stbi_uc *stbi_png_load (char const *filename, int *x, int *y, int *comp, int req_comp);
522 1.1.8.2 jruoho extern int stbi_png_info (char const *filename, int *x, int *y, int *comp);
523 1.1.8.2 jruoho extern int stbi_png_test_file (FILE *f);
524 1.1.8.2 jruoho extern stbi_uc *stbi_png_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
525 1.1.8.2 jruoho extern int stbi_png_info_from_file (FILE *f, int *x, int *y, int *comp);
526 1.1.8.2 jruoho #endif
527 1.1.8.2 jruoho
528 1.1.8.2 jruoho // is it a bmp?
529 1.1.8.2 jruoho extern int stbi_bmp_test_memory (stbi_uc const *buffer, int len);
530 1.1.8.2 jruoho
531 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load (char const *filename, int *x, int *y, int *comp, int req_comp);
532 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
533 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
534 1.1.8.2 jruoho extern int stbi_bmp_test_file (FILE *f);
535 1.1.8.2 jruoho extern stbi_uc *stbi_bmp_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
536 1.1.8.2 jruoho #endif
537 1.1.8.2 jruoho
538 1.1.8.2 jruoho // is it a tga?
539 1.1.8.2 jruoho extern int stbi_tga_test_memory (stbi_uc const *buffer, int len);
540 1.1.8.2 jruoho
541 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load (char const *filename, int *x, int *y, int *comp, int req_comp);
542 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
543 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
544 1.1.8.2 jruoho extern int stbi_tga_test_file (FILE *f);
545 1.1.8.2 jruoho extern stbi_uc *stbi_tga_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
546 1.1.8.2 jruoho #endif
547 1.1.8.2 jruoho
548 1.1.8.2 jruoho // is it a psd?
549 1.1.8.2 jruoho extern int stbi_psd_test_memory (stbi_uc const *buffer, int len);
550 1.1.8.2 jruoho
551 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load (char const *filename, int *x, int *y, int *comp, int req_comp);
552 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
553 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
554 1.1.8.2 jruoho extern int stbi_psd_test_file (FILE *f);
555 1.1.8.2 jruoho extern stbi_uc *stbi_psd_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
556 1.1.8.2 jruoho #endif
557 1.1.8.2 jruoho
558 1.1.8.2 jruoho // is it an hdr?
559 1.1.8.2 jruoho extern int stbi_hdr_test_memory (stbi_uc const *buffer, int len);
560 1.1.8.2 jruoho
561 1.1.8.2 jruoho extern float * stbi_hdr_load (char const *filename, int *x, int *y, int *comp, int req_comp);
562 1.1.8.2 jruoho extern float * stbi_hdr_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
563 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
564 1.1.8.2 jruoho extern int stbi_hdr_test_file (FILE *f);
565 1.1.8.2 jruoho extern float * stbi_hdr_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
566 1.1.8.2 jruoho #endif
567 1.1.8.2 jruoho
568 1.1.8.2 jruoho // is it a pic?
569 1.1.8.2 jruoho extern int stbi_pic_test_memory (stbi_uc const *buffer, int len);
570 1.1.8.2 jruoho
571 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load (char const *filename, int *x, int *y, int *comp, int req_comp);
572 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
573 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
574 1.1.8.2 jruoho extern int stbi_pic_test_file (FILE *f);
575 1.1.8.2 jruoho extern stbi_uc *stbi_pic_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
576 1.1.8.2 jruoho #endif
577 1.1.8.2 jruoho
578 1.1.8.2 jruoho // is it a gif?
579 1.1.8.2 jruoho extern int stbi_gif_test_memory (stbi_uc const *buffer, int len);
580 1.1.8.2 jruoho
581 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load (char const *filename, int *x, int *y, int *comp, int req_comp);
582 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp);
583 1.1.8.2 jruoho extern int stbi_gif_info_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp);
584 1.1.8.2 jruoho
585 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
586 1.1.8.2 jruoho extern int stbi_gif_test_file (FILE *f);
587 1.1.8.2 jruoho extern stbi_uc *stbi_gif_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp);
588 1.1.8.2 jruoho extern int stbi_gif_info (char const *filename, int *x, int *y, int *comp);
589 1.1.8.2 jruoho extern int stbi_gif_info_from_file (FILE *f, int *x, int *y, int *comp);
590 1.1.8.2 jruoho #endif
591 1.1.8.2 jruoho
592 1.1.8.2 jruoho
593 1.1.8.2 jruoho // this is not threadsafe
594 1.1.8.2 jruoho static const char *failure_reason;
595 1.1.8.2 jruoho
596 1.1.8.2 jruoho const char *stbi_failure_reason(void)
597 1.1.8.2 jruoho {
598 1.1.8.2 jruoho return failure_reason;
599 1.1.8.2 jruoho }
600 1.1.8.2 jruoho
601 1.1.8.2 jruoho #ifndef STBI_NO_FAILURE_STRINGS
602 1.1.8.2 jruoho static int e(const char *str)
603 1.1.8.2 jruoho {
604 1.1.8.2 jruoho failure_reason = str;
605 1.1.8.2 jruoho return 0;
606 1.1.8.2 jruoho }
607 1.1.8.2 jruoho #endif
608 1.1.8.2 jruoho
609 1.1.8.2 jruoho #ifdef STBI_NO_FAILURE_STRINGS
610 1.1.8.2 jruoho #define e(x,y) 0
611 1.1.8.2 jruoho #elif defined(STBI_FAILURE_USERMSG)
612 1.1.8.2 jruoho #define e(x,y) e(y)
613 1.1.8.2 jruoho #else
614 1.1.8.2 jruoho #define e(x,y) e(x)
615 1.1.8.2 jruoho #endif
616 1.1.8.2 jruoho
617 1.1.8.2 jruoho #define epf(x,y) ((float *) (e(x,y)?NULL:NULL))
618 1.1.8.2 jruoho #define epuc(x,y) ((unsigned char *) (e(x,y)?NULL:NULL))
619 1.1.8.2 jruoho
620 1.1.8.2 jruoho void stbi_image_free(void *retval_from_stbi_load)
621 1.1.8.2 jruoho {
622 1.1.8.2 jruoho FREE(retval_from_stbi_load);
623 1.1.8.2 jruoho }
624 1.1.8.2 jruoho
625 1.1.8.2 jruoho #define MAX_LOADERS 32
626 1.1.8.2 jruoho stbi_loader *loaders[MAX_LOADERS];
627 1.1.8.2 jruoho static int max_loaders = 0;
628 1.1.8.2 jruoho
629 1.1.8.2 jruoho int stbi_register_loader(stbi_loader *loader)
630 1.1.8.2 jruoho {
631 1.1.8.2 jruoho int i;
632 1.1.8.2 jruoho for (i=0; i < MAX_LOADERS; ++i) {
633 1.1.8.2 jruoho // already present?
634 1.1.8.2 jruoho if (loaders[i] == loader)
635 1.1.8.2 jruoho return 1;
636 1.1.8.2 jruoho // end of the list?
637 1.1.8.2 jruoho if (loaders[i] == NULL) {
638 1.1.8.2 jruoho loaders[i] = loader;
639 1.1.8.2 jruoho max_loaders = i+1;
640 1.1.8.2 jruoho return 1;
641 1.1.8.2 jruoho }
642 1.1.8.2 jruoho }
643 1.1.8.2 jruoho // no room for it
644 1.1.8.2 jruoho return 0;
645 1.1.8.2 jruoho }
646 1.1.8.2 jruoho
647 1.1.8.2 jruoho #ifndef STBI_NO_HDR
648 1.1.8.2 jruoho static float *ldr_to_hdr(stbi_uc *data, int x, int y, int comp);
649 1.1.8.2 jruoho static stbi_uc *hdr_to_ldr(float *data, int x, int y, int comp);
650 1.1.8.2 jruoho #endif
651 1.1.8.2 jruoho
652 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
653 1.1.8.2 jruoho unsigned char *stbi_load(char const *filename, int *x, int *y, int *comp, int req_comp)
654 1.1.8.2 jruoho {
655 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
656 1.1.8.2 jruoho unsigned char *result;
657 1.1.8.2 jruoho if (!f) return epuc("can't fopen", "Unable to open file");
658 1.1.8.2 jruoho result = stbi_load_from_file(f,x,y,comp,req_comp);
659 1.1.8.2 jruoho fclose(f);
660 1.1.8.2 jruoho return result;
661 1.1.8.2 jruoho }
662 1.1.8.2 jruoho
663 1.1.8.2 jruoho unsigned char *stbi_load_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
664 1.1.8.2 jruoho {
665 1.1.8.2 jruoho int i;
666 1.1.8.2 jruoho if (stbi_jpeg_test_file(f)) return stbi_jpeg_load_from_file(f,x,y,comp,req_comp);
667 1.1.8.2 jruoho if (stbi_png_test_file(f)) return stbi_png_load_from_file(f,x,y,comp,req_comp);
668 1.1.8.2 jruoho if (stbi_bmp_test_file(f)) return stbi_bmp_load_from_file(f,x,y,comp,req_comp);
669 1.1.8.2 jruoho if (stbi_gif_test_file(f)) return stbi_gif_load_from_file(f,x,y,comp,req_comp);
670 1.1.8.2 jruoho if (stbi_psd_test_file(f)) return stbi_psd_load_from_file(f,x,y,comp,req_comp);
671 1.1.8.2 jruoho if (stbi_pic_test_file(f)) return stbi_pic_load_from_file(f,x,y,comp,req_comp);
672 1.1.8.2 jruoho
673 1.1.8.2 jruoho #ifndef STBI_NO_HDR
674 1.1.8.2 jruoho if (stbi_hdr_test_file(f)) {
675 1.1.8.2 jruoho float *hdr = stbi_hdr_load_from_file(f, x,y,comp,req_comp);
676 1.1.8.2 jruoho return hdr_to_ldr(hdr, *x, *y, req_comp ? req_comp : *comp);
677 1.1.8.2 jruoho }
678 1.1.8.2 jruoho #endif
679 1.1.8.2 jruoho
680 1.1.8.2 jruoho for (i=0; i < max_loaders; ++i)
681 1.1.8.2 jruoho if (loaders[i]->test_file(f))
682 1.1.8.2 jruoho return loaders[i]->load_from_file(f,x,y,comp,req_comp);
683 1.1.8.2 jruoho // test tga last because it's a crappy test!
684 1.1.8.2 jruoho if (stbi_tga_test_file(f))
685 1.1.8.2 jruoho return stbi_tga_load_from_file(f,x,y,comp,req_comp);
686 1.1.8.2 jruoho return epuc("unknown image type", "Image not of any known type, or corrupt");
687 1.1.8.2 jruoho }
688 1.1.8.2 jruoho #endif
689 1.1.8.2 jruoho
690 1.1.8.2 jruoho unsigned char *stbi_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
691 1.1.8.2 jruoho {
692 1.1.8.2 jruoho int i;
693 1.1.8.2 jruoho if (stbi_jpeg_test_memory(buffer,len)) return stbi_jpeg_load_from_memory(buffer,len,x,y,comp,req_comp);
694 1.1.8.2 jruoho if (stbi_png_test_memory(buffer,len)) return stbi_png_load_from_memory(buffer,len,x,y,comp,req_comp);
695 1.1.8.2 jruoho if (stbi_bmp_test_memory(buffer,len)) return stbi_bmp_load_from_memory(buffer,len,x,y,comp,req_comp);
696 1.1.8.2 jruoho if (stbi_gif_test_memory(buffer,len)) return stbi_gif_load_from_memory(buffer,len,x,y,comp,req_comp);
697 1.1.8.2 jruoho if (stbi_psd_test_memory(buffer,len)) return stbi_psd_load_from_memory(buffer,len,x,y,comp,req_comp);
698 1.1.8.2 jruoho if (stbi_pic_test_memory(buffer,len)) return stbi_pic_load_from_memory(buffer,len,x,y,comp,req_comp);
699 1.1.8.2 jruoho
700 1.1.8.2 jruoho #ifndef STBI_NO_HDR
701 1.1.8.2 jruoho if (stbi_hdr_test_memory(buffer, len)) {
702 1.1.8.2 jruoho float *hdr = stbi_hdr_load_from_memory(buffer, len,x,y,comp,req_comp);
703 1.1.8.2 jruoho return hdr_to_ldr(hdr, *x, *y, req_comp ? req_comp : *comp);
704 1.1.8.2 jruoho }
705 1.1.8.2 jruoho #endif
706 1.1.8.2 jruoho
707 1.1.8.2 jruoho for (i=0; i < max_loaders; ++i)
708 1.1.8.2 jruoho if (loaders[i]->test_memory(buffer,len))
709 1.1.8.2 jruoho return loaders[i]->load_from_memory(buffer,len,x,y,comp,req_comp);
710 1.1.8.2 jruoho // test tga last because it's a crappy test!
711 1.1.8.2 jruoho if (stbi_tga_test_memory(buffer,len))
712 1.1.8.2 jruoho return stbi_tga_load_from_memory(buffer,len,x,y,comp,req_comp);
713 1.1.8.2 jruoho return epuc("unknown image type", "Image not of any known type, or corrupt");
714 1.1.8.2 jruoho }
715 1.1.8.2 jruoho
716 1.1.8.2 jruoho #ifndef STBI_NO_HDR
717 1.1.8.2 jruoho
718 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
719 1.1.8.2 jruoho float *stbi_loadf(char const *filename, int *x, int *y, int *comp, int req_comp)
720 1.1.8.2 jruoho {
721 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
722 1.1.8.2 jruoho float *result;
723 1.1.8.2 jruoho if (!f) return epf("can't fopen", "Unable to open file");
724 1.1.8.2 jruoho result = stbi_loadf_from_file(f,x,y,comp,req_comp);
725 1.1.8.2 jruoho fclose(f);
726 1.1.8.2 jruoho return result;
727 1.1.8.2 jruoho }
728 1.1.8.2 jruoho
729 1.1.8.2 jruoho float *stbi_loadf_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
730 1.1.8.2 jruoho {
731 1.1.8.2 jruoho unsigned char *data;
732 1.1.8.2 jruoho #ifndef STBI_NO_HDR
733 1.1.8.2 jruoho if (stbi_hdr_test_file(f))
734 1.1.8.2 jruoho return stbi_hdr_load_from_file(f,x,y,comp,req_comp);
735 1.1.8.2 jruoho #endif
736 1.1.8.2 jruoho data = stbi_load_from_file(f, x, y, comp, req_comp);
737 1.1.8.2 jruoho if (data)
738 1.1.8.2 jruoho return ldr_to_hdr(data, *x, *y, req_comp ? req_comp : *comp);
739 1.1.8.2 jruoho return epf("unknown image type", "Image not of any known type, or corrupt");
740 1.1.8.2 jruoho }
741 1.1.8.2 jruoho #endif
742 1.1.8.2 jruoho
743 1.1.8.2 jruoho float *stbi_loadf_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
744 1.1.8.2 jruoho {
745 1.1.8.2 jruoho stbi_uc *data;
746 1.1.8.2 jruoho #ifndef STBI_NO_HDR
747 1.1.8.2 jruoho if (stbi_hdr_test_memory(buffer, len))
748 1.1.8.2 jruoho return stbi_hdr_load_from_memory(buffer, len,x,y,comp,req_comp);
749 1.1.8.2 jruoho #endif
750 1.1.8.2 jruoho data = stbi_load_from_memory(buffer, len, x, y, comp, req_comp);
751 1.1.8.2 jruoho if (data)
752 1.1.8.2 jruoho return ldr_to_hdr(data, *x, *y, req_comp ? req_comp : *comp);
753 1.1.8.2 jruoho return epf("unknown image type", "Image not of any known type, or corrupt");
754 1.1.8.2 jruoho }
755 1.1.8.2 jruoho #endif
756 1.1.8.2 jruoho
757 1.1.8.2 jruoho // these is-hdr-or-not is defined independent of whether STBI_NO_HDR is
758 1.1.8.2 jruoho // defined, for API simplicity; if STBI_NO_HDR is defined, it always
759 1.1.8.2 jruoho // reports false!
760 1.1.8.2 jruoho
761 1.1.8.2 jruoho int stbi_is_hdr_from_memory(stbi_uc const *buffer, int len)
762 1.1.8.2 jruoho {
763 1.1.8.2 jruoho #ifndef STBI_NO_HDR
764 1.1.8.2 jruoho return stbi_hdr_test_memory(buffer, len);
765 1.1.8.2 jruoho #else
766 1.1.8.2 jruoho STBI_NOTUSED(buffer);
767 1.1.8.2 jruoho STBI_NOTUSED(len);
768 1.1.8.2 jruoho return 0;
769 1.1.8.2 jruoho #endif
770 1.1.8.2 jruoho }
771 1.1.8.2 jruoho
772 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
773 1.1.8.2 jruoho extern int stbi_is_hdr (char const *filename)
774 1.1.8.2 jruoho {
775 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
776 1.1.8.2 jruoho int result=0;
777 1.1.8.2 jruoho if (f) {
778 1.1.8.2 jruoho result = stbi_is_hdr_from_file(f);
779 1.1.8.2 jruoho fclose(f);
780 1.1.8.2 jruoho }
781 1.1.8.2 jruoho return result;
782 1.1.8.2 jruoho }
783 1.1.8.2 jruoho
784 1.1.8.2 jruoho extern int stbi_is_hdr_from_file(FILE *f)
785 1.1.8.2 jruoho {
786 1.1.8.2 jruoho #ifndef STBI_NO_HDR
787 1.1.8.2 jruoho return stbi_hdr_test_file(f);
788 1.1.8.2 jruoho #else
789 1.1.8.2 jruoho return 0;
790 1.1.8.2 jruoho #endif
791 1.1.8.2 jruoho }
792 1.1.8.2 jruoho
793 1.1.8.2 jruoho #endif
794 1.1.8.2 jruoho
795 1.1.8.2 jruoho #ifndef STBI_NO_HDR
796 1.1.8.2 jruoho static float h2l_gamma_i=1.0f/2.2f, h2l_scale_i=1.0f;
797 1.1.8.2 jruoho static float l2h_gamma=2.2f, l2h_scale=1.0f;
798 1.1.8.2 jruoho
799 1.1.8.2 jruoho void stbi_hdr_to_ldr_gamma(float gamma) { h2l_gamma_i = 1/gamma; }
800 1.1.8.2 jruoho void stbi_hdr_to_ldr_scale(float scale) { h2l_scale_i = 1/scale; }
801 1.1.8.2 jruoho
802 1.1.8.2 jruoho void stbi_ldr_to_hdr_gamma(float gamma) { l2h_gamma = gamma; }
803 1.1.8.2 jruoho void stbi_ldr_to_hdr_scale(float scale) { l2h_scale = scale; }
804 1.1.8.2 jruoho #endif
805 1.1.8.2 jruoho
806 1.1.8.2 jruoho
807 1.1.8.2 jruoho //////////////////////////////////////////////////////////////////////////////
808 1.1.8.2 jruoho //
809 1.1.8.2 jruoho // Common code used by all image loaders
810 1.1.8.2 jruoho //
811 1.1.8.2 jruoho
812 1.1.8.2 jruoho enum
813 1.1.8.2 jruoho {
814 1.1.8.2 jruoho SCAN_load=0,
815 1.1.8.2 jruoho SCAN_type,
816 1.1.8.2 jruoho SCAN_header
817 1.1.8.2 jruoho };
818 1.1.8.2 jruoho
819 1.1.8.2 jruoho typedef struct
820 1.1.8.2 jruoho {
821 1.1.8.2 jruoho uint32 img_x, img_y;
822 1.1.8.2 jruoho int img_n, img_out_n;
823 1.1.8.2 jruoho
824 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
825 1.1.8.2 jruoho FILE *img_file;
826 1.1.8.2 jruoho int buflen;
827 1.1.8.2 jruoho uint8 buffer_start[128];
828 1.1.8.2 jruoho int from_file;
829 1.1.8.2 jruoho #endif
830 1.1.8.2 jruoho uint8 const *img_buffer, *img_buffer_end;
831 1.1.8.2 jruoho } stbi;
832 1.1.8.2 jruoho
833 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
834 1.1.8.2 jruoho static void start_file(stbi *s, FILE *f)
835 1.1.8.2 jruoho {
836 1.1.8.2 jruoho s->img_file = f;
837 1.1.8.2 jruoho s->buflen = sizeof(s->buffer_start);
838 1.1.8.2 jruoho s->img_buffer_end = s->buffer_start + s->buflen;
839 1.1.8.2 jruoho s->img_buffer = s->img_buffer_end;
840 1.1.8.2 jruoho s->from_file = 1;
841 1.1.8.2 jruoho }
842 1.1.8.2 jruoho #endif
843 1.1.8.2 jruoho
844 1.1.8.2 jruoho static void start_mem(stbi *s, uint8 const *buffer, int len)
845 1.1.8.2 jruoho {
846 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
847 1.1.8.2 jruoho s->img_file = NULL;
848 1.1.8.2 jruoho s->from_file = 0;
849 1.1.8.2 jruoho #endif
850 1.1.8.2 jruoho s->img_buffer = (uint8 const *) buffer;
851 1.1.8.2 jruoho s->img_buffer_end = (uint8 const *) buffer+len;
852 1.1.8.2 jruoho }
853 1.1.8.2 jruoho
854 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
855 1.1.8.2 jruoho static void refill_buffer(stbi *s)
856 1.1.8.2 jruoho {
857 1.1.8.2 jruoho int n = fread(s->buffer_start, 1, s->buflen, s->img_file);
858 1.1.8.2 jruoho if (n == 0) {
859 1.1.8.2 jruoho s->from_file = 0;
860 1.1.8.2 jruoho s->img_buffer = s->img_buffer_end-1;
861 1.1.8.2 jruoho #if 0
862 1.1.8.2 jruoho *s->img_buffer = 0;
863 1.1.8.2 jruoho #endif
864 1.1.8.2 jruoho } else {
865 1.1.8.2 jruoho s->img_buffer = s->buffer_start;
866 1.1.8.2 jruoho s->img_buffer_end = s->buffer_start + n;
867 1.1.8.2 jruoho }
868 1.1.8.2 jruoho }
869 1.1.8.2 jruoho #endif
870 1.1.8.2 jruoho
871 1.1.8.2 jruoho __forceinline static int get8(stbi *s)
872 1.1.8.2 jruoho {
873 1.1.8.2 jruoho if (s->img_buffer < s->img_buffer_end)
874 1.1.8.2 jruoho return *s->img_buffer++;
875 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
876 1.1.8.2 jruoho if (s->from_file) {
877 1.1.8.2 jruoho refill_buffer(s);
878 1.1.8.2 jruoho return *s->img_buffer++;
879 1.1.8.2 jruoho }
880 1.1.8.2 jruoho #endif
881 1.1.8.2 jruoho return 0;
882 1.1.8.2 jruoho }
883 1.1.8.2 jruoho
884 1.1.8.2 jruoho __forceinline static int at_eof(stbi *s)
885 1.1.8.2 jruoho {
886 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
887 1.1.8.2 jruoho if (s->img_file) {
888 1.1.8.2 jruoho if (!feof(s->img_file)) return 0;
889 1.1.8.2 jruoho // if feof() is true, check if buffer = end
890 1.1.8.2 jruoho // special case: we've only got the special 0 character at the end
891 1.1.8.2 jruoho if (s->from_file == 0) return 1;
892 1.1.8.2 jruoho }
893 1.1.8.2 jruoho #endif
894 1.1.8.2 jruoho return s->img_buffer >= s->img_buffer_end;
895 1.1.8.2 jruoho }
896 1.1.8.2 jruoho
897 1.1.8.2 jruoho __forceinline static uint8 get8u(stbi *s)
898 1.1.8.2 jruoho {
899 1.1.8.2 jruoho return (uint8) get8(s);
900 1.1.8.2 jruoho }
901 1.1.8.2 jruoho
902 1.1.8.2 jruoho static void skip(stbi *s, int n)
903 1.1.8.2 jruoho {
904 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
905 1.1.8.2 jruoho if (s->img_file) {
906 1.1.8.2 jruoho int blen = s->img_buffer_end - s->img_buffer;
907 1.1.8.2 jruoho if (blen < n) {
908 1.1.8.2 jruoho s->img_buffer = s->img_buffer_end;
909 1.1.8.2 jruoho fseek(s->img_file, n - blen, SEEK_CUR);
910 1.1.8.2 jruoho return;
911 1.1.8.2 jruoho }
912 1.1.8.2 jruoho }
913 1.1.8.2 jruoho #endif
914 1.1.8.2 jruoho s->img_buffer += n;
915 1.1.8.2 jruoho }
916 1.1.8.2 jruoho
917 1.1.8.2 jruoho static int getn(stbi *s, stbi_uc *buffer, int n)
918 1.1.8.2 jruoho {
919 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
920 1.1.8.2 jruoho if (s->img_file) {
921 1.1.8.2 jruoho int blen = s->img_buffer_end - s->img_buffer;
922 1.1.8.2 jruoho if (blen < n) {
923 1.1.8.2 jruoho int res;
924 1.1.8.2 jruoho memcpy(buffer, s->img_buffer, blen);
925 1.1.8.2 jruoho res = ((int) fread(buffer + blen, 1, n - blen, s->img_file) == (n-blen));
926 1.1.8.2 jruoho s->img_buffer = s->img_buffer_end;
927 1.1.8.2 jruoho return res;
928 1.1.8.2 jruoho }
929 1.1.8.2 jruoho }
930 1.1.8.2 jruoho #endif
931 1.1.8.2 jruoho if (s->img_buffer+n <= s->img_buffer_end) {
932 1.1.8.2 jruoho memcpy(buffer, s->img_buffer, n);
933 1.1.8.2 jruoho s->img_buffer += n;
934 1.1.8.2 jruoho return 1;
935 1.1.8.2 jruoho } else
936 1.1.8.2 jruoho return 0;
937 1.1.8.2 jruoho }
938 1.1.8.2 jruoho
939 1.1.8.2 jruoho static int get16(stbi *s)
940 1.1.8.2 jruoho {
941 1.1.8.2 jruoho int z = get8(s);
942 1.1.8.2 jruoho return (z << 8) + get8(s);
943 1.1.8.2 jruoho }
944 1.1.8.2 jruoho
945 1.1.8.2 jruoho static uint32 get32(stbi *s)
946 1.1.8.2 jruoho {
947 1.1.8.2 jruoho uint32 z = get16(s);
948 1.1.8.2 jruoho return (z << 16) + get16(s);
949 1.1.8.2 jruoho }
950 1.1.8.2 jruoho
951 1.1.8.2 jruoho static int get16le(stbi *s)
952 1.1.8.2 jruoho {
953 1.1.8.2 jruoho int z = get8(s);
954 1.1.8.2 jruoho return z + (get8(s) << 8);
955 1.1.8.2 jruoho }
956 1.1.8.2 jruoho
957 1.1.8.2 jruoho static uint32 get32le(stbi *s)
958 1.1.8.2 jruoho {
959 1.1.8.2 jruoho uint32 z = get16le(s);
960 1.1.8.2 jruoho return z + (get16le(s) << 16);
961 1.1.8.2 jruoho }
962 1.1.8.2 jruoho
963 1.1.8.2 jruoho //////////////////////////////////////////////////////////////////////////////
964 1.1.8.2 jruoho //
965 1.1.8.2 jruoho // generic converter from built-in img_n to req_comp
966 1.1.8.2 jruoho // individual types do this automatically as much as possible (e.g. jpeg
967 1.1.8.2 jruoho // does all cases internally since it needs to colorspace convert anyway,
968 1.1.8.2 jruoho // and it never has alpha, so very few cases ). png can automatically
969 1.1.8.2 jruoho // interleave an alpha=255 channel, but falls back to this for other cases
970 1.1.8.2 jruoho //
971 1.1.8.2 jruoho // assume data buffer is malloced, so malloc a new one and free that one
972 1.1.8.2 jruoho // only failure mode is malloc failing
973 1.1.8.2 jruoho
974 1.1.8.2 jruoho static uint8 compute_y(int r, int g, int b)
975 1.1.8.2 jruoho {
976 1.1.8.2 jruoho return (uint8) (((r*77) + (g*150) + (29*b)) >> 8);
977 1.1.8.2 jruoho }
978 1.1.8.2 jruoho
979 1.1.8.2 jruoho static unsigned char *convert_format(unsigned char *data, int img_n, int req_comp, uint x, uint y)
980 1.1.8.2 jruoho {
981 1.1.8.2 jruoho int i,j;
982 1.1.8.2 jruoho unsigned char *good;
983 1.1.8.2 jruoho
984 1.1.8.2 jruoho if (req_comp == img_n) return data;
985 1.1.8.2 jruoho assert(req_comp >= 1 && req_comp <= 4);
986 1.1.8.2 jruoho
987 1.1.8.2 jruoho good = (unsigned char *) MALLOC(req_comp * x * y);
988 1.1.8.2 jruoho if (good == NULL) {
989 1.1.8.2 jruoho FREE(data);
990 1.1.8.2 jruoho return epuc("outofmem", "Out of memory");
991 1.1.8.2 jruoho }
992 1.1.8.2 jruoho
993 1.1.8.2 jruoho for (j=0; j < (int) y; ++j) {
994 1.1.8.2 jruoho unsigned char *src = data + j * x * img_n ;
995 1.1.8.2 jruoho unsigned char *dest = good + j * x * req_comp;
996 1.1.8.2 jruoho
997 1.1.8.2 jruoho #define COMBO(a,b) ((a)*8+(b))
998 1.1.8.2 jruoho #define CASE(a,b) case COMBO(a,b): for(i=x-1; i >= 0; --i, src += a, dest += b)
999 1.1.8.2 jruoho // convert source image with img_n components to one with req_comp components;
1000 1.1.8.2 jruoho // avoid switch per pixel, so use switch per scanline and massive macros
1001 1.1.8.2 jruoho switch (COMBO(img_n, req_comp)) {
1002 1.1.8.2 jruoho CASE(1,2) dest[0]=src[0], dest[1]=255; break;
1003 1.1.8.2 jruoho CASE(1,3) dest[0]=dest[1]=dest[2]=src[0]; break;
1004 1.1.8.2 jruoho CASE(1,4) dest[0]=dest[1]=dest[2]=src[0], dest[3]=255; break;
1005 1.1.8.2 jruoho CASE(2,1) dest[0]=src[0]; break;
1006 1.1.8.2 jruoho CASE(2,3) dest[0]=dest[1]=dest[2]=src[0]; break;
1007 1.1.8.2 jruoho CASE(2,4) dest[0]=dest[1]=dest[2]=src[0], dest[3]=src[1]; break;
1008 1.1.8.2 jruoho CASE(3,4) dest[0]=src[0],dest[1]=src[1],dest[2]=src[2],dest[3]=255; break;
1009 1.1.8.2 jruoho CASE(3,1) dest[0]=compute_y(src[0],src[1],src[2]); break;
1010 1.1.8.2 jruoho CASE(3,2) dest[0]=compute_y(src[0],src[1],src[2]), dest[1] = 255; break;
1011 1.1.8.2 jruoho CASE(4,1) dest[0]=compute_y(src[0],src[1],src[2]); break;
1012 1.1.8.2 jruoho CASE(4,2) dest[0]=compute_y(src[0],src[1],src[2]), dest[1] = src[3]; break;
1013 1.1.8.2 jruoho CASE(4,3) dest[0]=src[0],dest[1]=src[1],dest[2]=src[2]; break;
1014 1.1.8.2 jruoho default: assert(0);
1015 1.1.8.2 jruoho }
1016 1.1.8.2 jruoho #undef CASE
1017 1.1.8.2 jruoho }
1018 1.1.8.2 jruoho
1019 1.1.8.2 jruoho FREE(data);
1020 1.1.8.2 jruoho return good;
1021 1.1.8.2 jruoho }
1022 1.1.8.2 jruoho
1023 1.1.8.2 jruoho #ifndef STBI_NO_HDR
1024 1.1.8.2 jruoho static float *ldr_to_hdr(stbi_uc *data, int x, int y, int comp)
1025 1.1.8.2 jruoho {
1026 1.1.8.2 jruoho int i,k,n;
1027 1.1.8.2 jruoho float *output = (float *) MALLOC(x * y * comp * sizeof(float));
1028 1.1.8.2 jruoho if (output == NULL) { FREE(data); return epf("outofmem", "Out of memory"); }
1029 1.1.8.2 jruoho // compute number of non-alpha components
1030 1.1.8.2 jruoho if (comp & 1) n = comp; else n = comp-1;
1031 1.1.8.2 jruoho for (i=0; i < x*y; ++i) {
1032 1.1.8.2 jruoho for (k=0; k < n; ++k) {
1033 1.1.8.2 jruoho output[i*comp + k] = (float) pow(data[i*comp+k]/255.0f, l2h_gamma) * l2h_scale;
1034 1.1.8.2 jruoho }
1035 1.1.8.2 jruoho if (k < comp) output[i*comp + k] = data[i*comp+k]/255.0f;
1036 1.1.8.2 jruoho }
1037 1.1.8.2 jruoho FREE(data);
1038 1.1.8.2 jruoho return output;
1039 1.1.8.2 jruoho }
1040 1.1.8.2 jruoho
1041 1.1.8.2 jruoho #define float2int(x) ((int) (x))
1042 1.1.8.2 jruoho static stbi_uc *hdr_to_ldr(float *data, int x, int y, int comp)
1043 1.1.8.2 jruoho {
1044 1.1.8.2 jruoho int i,k,n;
1045 1.1.8.2 jruoho stbi_uc *output = (stbi_uc *) MALLOC(x * y * comp);
1046 1.1.8.2 jruoho if (output == NULL) { FREE(data); return epuc("outofmem", "Out of memory"); }
1047 1.1.8.2 jruoho // compute number of non-alpha components
1048 1.1.8.2 jruoho if (comp & 1) n = comp; else n = comp-1;
1049 1.1.8.2 jruoho for (i=0; i < x*y; ++i) {
1050 1.1.8.2 jruoho for (k=0; k < n; ++k) {
1051 1.1.8.2 jruoho float z = (float) pow(data[i*comp+k]*h2l_scale_i, h2l_gamma_i) * 255 + 0.5f;
1052 1.1.8.2 jruoho if (z < 0) z = 0;
1053 1.1.8.2 jruoho if (z > 255) z = 255;
1054 1.1.8.2 jruoho output[i*comp + k] = (uint8) float2int(z);
1055 1.1.8.2 jruoho }
1056 1.1.8.2 jruoho if (k < comp) {
1057 1.1.8.2 jruoho float z = data[i*comp+k] * 255 + 0.5f;
1058 1.1.8.2 jruoho if (z < 0) z = 0;
1059 1.1.8.2 jruoho if (z > 255) z = 255;
1060 1.1.8.2 jruoho output[i*comp + k] = (uint8) float2int(z);
1061 1.1.8.2 jruoho }
1062 1.1.8.2 jruoho }
1063 1.1.8.2 jruoho FREE(data);
1064 1.1.8.2 jruoho return output;
1065 1.1.8.2 jruoho }
1066 1.1.8.2 jruoho #endif
1067 1.1.8.2 jruoho
1068 1.1.8.2 jruoho //////////////////////////////////////////////////////////////////////////////
1069 1.1.8.2 jruoho //
1070 1.1.8.2 jruoho // "baseline" JPEG/JFIF decoder (not actually fully baseline implementation)
1071 1.1.8.2 jruoho //
1072 1.1.8.2 jruoho // simple implementation
1073 1.1.8.2 jruoho // - channel subsampling of at most 2 in each dimension
1074 1.1.8.2 jruoho // - doesn't support delayed output of y-dimension
1075 1.1.8.2 jruoho // - simple interface (only one output format: 8-bit interleaved RGB)
1076 1.1.8.2 jruoho // - doesn't try to recover corrupt jpegs
1077 1.1.8.2 jruoho // - doesn't allow partial loading, loading multiple at once
1078 1.1.8.2 jruoho // - still fast on x86 (copying globals into locals doesn't help x86)
1079 1.1.8.2 jruoho // - allocates lots of intermediate memory (full size of all components)
1080 1.1.8.2 jruoho // - non-interleaved case requires this anyway
1081 1.1.8.2 jruoho // - allows good upsampling (see next)
1082 1.1.8.2 jruoho // high-quality
1083 1.1.8.2 jruoho // - upsampled channels are bilinearly interpolated, even across blocks
1084 1.1.8.2 jruoho // - quality integer IDCT derived from IJG's 'slow'
1085 1.1.8.2 jruoho // performance
1086 1.1.8.2 jruoho // - fast huffman; reasonable integer IDCT
1087 1.1.8.2 jruoho // - uses a lot of intermediate memory, could cache poorly
1088 1.1.8.2 jruoho // - load http://nothings.org/remote/anemones.jpg 3 times on 2.8Ghz P4
1089 1.1.8.2 jruoho // stb_jpeg: 1.34 seconds (MSVC6, default release build)
1090 1.1.8.2 jruoho // stb_jpeg: 1.06 seconds (MSVC6, processor = Pentium Pro)
1091 1.1.8.2 jruoho // IJL11.dll: 1.08 seconds (compiled by intel)
1092 1.1.8.2 jruoho // IJG 1998: 0.98 seconds (MSVC6, makefile provided by IJG)
1093 1.1.8.2 jruoho // IJG 1998: 0.95 seconds (MSVC6, makefile + proc=PPro)
1094 1.1.8.2 jruoho
1095 1.1.8.2 jruoho // huffman decoding acceleration
1096 1.1.8.2 jruoho #define FAST_BITS 9 // larger handles more cases; smaller stomps less cache
1097 1.1.8.2 jruoho
1098 1.1.8.2 jruoho typedef struct
1099 1.1.8.2 jruoho {
1100 1.1.8.2 jruoho uint8 fast[1 << FAST_BITS];
1101 1.1.8.2 jruoho // weirdly, repacking this into AoS is a 10% speed loss, instead of a win
1102 1.1.8.2 jruoho uint16 code[256];
1103 1.1.8.2 jruoho uint8 values[256];
1104 1.1.8.2 jruoho uint8 size[257];
1105 1.1.8.2 jruoho unsigned int maxcode[18];
1106 1.1.8.2 jruoho int delta[17]; // old 'firstsymbol' - old 'firstcode'
1107 1.1.8.2 jruoho } huffman;
1108 1.1.8.2 jruoho
1109 1.1.8.2 jruoho typedef struct
1110 1.1.8.2 jruoho {
1111 1.1.8.2 jruoho #ifdef STBI_SIMD
1112 1.1.8.2 jruoho unsigned short dequant2[4][64];
1113 1.1.8.2 jruoho #endif
1114 1.1.8.2 jruoho stbi s;
1115 1.1.8.2 jruoho huffman huff_dc[4];
1116 1.1.8.2 jruoho huffman huff_ac[4];
1117 1.1.8.2 jruoho uint8 dequant[4][64];
1118 1.1.8.2 jruoho
1119 1.1.8.2 jruoho // sizes for components, interleaved MCUs
1120 1.1.8.2 jruoho int img_h_max, img_v_max;
1121 1.1.8.2 jruoho int img_mcu_x, img_mcu_y;
1122 1.1.8.2 jruoho int img_mcu_w, img_mcu_h;
1123 1.1.8.2 jruoho
1124 1.1.8.2 jruoho // definition of jpeg image component
1125 1.1.8.2 jruoho struct
1126 1.1.8.2 jruoho {
1127 1.1.8.2 jruoho int id;
1128 1.1.8.2 jruoho int h,v;
1129 1.1.8.2 jruoho int tq;
1130 1.1.8.2 jruoho int hd,ha;
1131 1.1.8.2 jruoho int dc_pred;
1132 1.1.8.2 jruoho
1133 1.1.8.2 jruoho int x,y,w2,h2;
1134 1.1.8.2 jruoho uint8 *data;
1135 1.1.8.2 jruoho void *raw_data;
1136 1.1.8.2 jruoho uint8 *linebuf;
1137 1.1.8.2 jruoho } img_comp[4];
1138 1.1.8.2 jruoho
1139 1.1.8.2 jruoho uint32 code_buffer; // jpeg entropy-coded buffer
1140 1.1.8.2 jruoho int code_bits; // number of valid bits
1141 1.1.8.2 jruoho unsigned char marker; // marker seen while filling entropy buffer
1142 1.1.8.2 jruoho int nomore; // flag if we saw a marker so must stop
1143 1.1.8.2 jruoho
1144 1.1.8.2 jruoho int scan_n, order[4];
1145 1.1.8.2 jruoho int restart_interval, todo;
1146 1.1.8.2 jruoho } jpeg;
1147 1.1.8.2 jruoho
1148 1.1.8.2 jruoho static int build_huffman(huffman *h, int *count)
1149 1.1.8.2 jruoho {
1150 1.1.8.2 jruoho int i,j,k=0,code;
1151 1.1.8.2 jruoho // build size list for each symbol (from JPEG spec)
1152 1.1.8.2 jruoho for (i=0; i < 16; ++i)
1153 1.1.8.2 jruoho for (j=0; j < count[i]; ++j)
1154 1.1.8.2 jruoho h->size[k++] = (uint8) (i+1);
1155 1.1.8.2 jruoho h->size[k] = 0;
1156 1.1.8.2 jruoho
1157 1.1.8.2 jruoho // compute actual symbols (from jpeg spec)
1158 1.1.8.2 jruoho code = 0;
1159 1.1.8.2 jruoho k = 0;
1160 1.1.8.2 jruoho for(j=1; j <= 16; ++j) {
1161 1.1.8.2 jruoho // compute delta to add to code to compute symbol id
1162 1.1.8.2 jruoho h->delta[j] = k - code;
1163 1.1.8.2 jruoho if (h->size[k] == j) {
1164 1.1.8.2 jruoho while (h->size[k] == j)
1165 1.1.8.2 jruoho h->code[k++] = (uint16) (code++);
1166 1.1.8.2 jruoho if (code-1 >= (1 << j)) return e("bad code lengths","Corrupt JPEG");
1167 1.1.8.2 jruoho }
1168 1.1.8.2 jruoho // compute largest code + 1 for this size, preshifted as needed later
1169 1.1.8.2 jruoho h->maxcode[j] = code << (16-j);
1170 1.1.8.2 jruoho code <<= 1;
1171 1.1.8.2 jruoho }
1172 1.1.8.2 jruoho h->maxcode[j] = 0xffffffff;
1173 1.1.8.2 jruoho
1174 1.1.8.2 jruoho // build non-spec acceleration table; 255 is flag for not-accelerated
1175 1.1.8.2 jruoho memset(h->fast, 255, 1 << FAST_BITS);
1176 1.1.8.2 jruoho for (i=0; i < k; ++i) {
1177 1.1.8.2 jruoho int s = h->size[i];
1178 1.1.8.2 jruoho if (s <= FAST_BITS) {
1179 1.1.8.2 jruoho int c = h->code[i] << (FAST_BITS-s);
1180 1.1.8.2 jruoho int m = 1 << (FAST_BITS-s);
1181 1.1.8.2 jruoho for (j=0; j < m; ++j) {
1182 1.1.8.2 jruoho h->fast[c+j] = (uint8) i;
1183 1.1.8.2 jruoho }
1184 1.1.8.2 jruoho }
1185 1.1.8.2 jruoho }
1186 1.1.8.2 jruoho return 1;
1187 1.1.8.2 jruoho }
1188 1.1.8.2 jruoho
1189 1.1.8.2 jruoho static void grow_buffer_unsafe(jpeg *j)
1190 1.1.8.2 jruoho {
1191 1.1.8.2 jruoho do {
1192 1.1.8.2 jruoho int b = j->nomore ? 0 : get8(&j->s);
1193 1.1.8.2 jruoho if (b == 0xff) {
1194 1.1.8.2 jruoho int c = get8(&j->s);
1195 1.1.8.2 jruoho if (c != 0) {
1196 1.1.8.2 jruoho j->marker = (unsigned char) c;
1197 1.1.8.2 jruoho j->nomore = 1;
1198 1.1.8.2 jruoho return;
1199 1.1.8.2 jruoho }
1200 1.1.8.2 jruoho }
1201 1.1.8.2 jruoho j->code_buffer |= b << (24 - j->code_bits);
1202 1.1.8.2 jruoho j->code_bits += 8;
1203 1.1.8.2 jruoho } while (j->code_bits <= 24);
1204 1.1.8.2 jruoho }
1205 1.1.8.2 jruoho
1206 1.1.8.2 jruoho // (1 << n) - 1
1207 1.1.8.2 jruoho static uint32 bmask[17]={0,1,3,7,15,31,63,127,255,511,1023,2047,4095,8191,16383,32767,65535};
1208 1.1.8.2 jruoho
1209 1.1.8.2 jruoho // decode a jpeg huffman value from the bitstream
1210 1.1.8.2 jruoho __forceinline static int decode(jpeg *j, huffman *h)
1211 1.1.8.2 jruoho {
1212 1.1.8.2 jruoho unsigned int temp;
1213 1.1.8.2 jruoho int c,k;
1214 1.1.8.2 jruoho
1215 1.1.8.2 jruoho if (j->code_bits < 16) grow_buffer_unsafe(j);
1216 1.1.8.2 jruoho
1217 1.1.8.2 jruoho // look at the top FAST_BITS and determine what symbol ID it is,
1218 1.1.8.2 jruoho // if the code is <= FAST_BITS
1219 1.1.8.2 jruoho c = (j->code_buffer >> (32 - FAST_BITS)) & ((1 << FAST_BITS)-1);
1220 1.1.8.2 jruoho k = h->fast[c];
1221 1.1.8.2 jruoho if (k < 255) {
1222 1.1.8.2 jruoho int s = h->size[k];
1223 1.1.8.2 jruoho if (s > j->code_bits)
1224 1.1.8.2 jruoho return -1;
1225 1.1.8.2 jruoho j->code_buffer <<= s;
1226 1.1.8.2 jruoho j->code_bits -= s;
1227 1.1.8.2 jruoho return h->values[k];
1228 1.1.8.2 jruoho }
1229 1.1.8.2 jruoho
1230 1.1.8.2 jruoho // naive test is to shift the code_buffer down so k bits are
1231 1.1.8.2 jruoho // valid, then test against maxcode. To speed this up, we've
1232 1.1.8.2 jruoho // preshifted maxcode left so that it has (16-k) 0s at the
1233 1.1.8.2 jruoho // end; in other words, regardless of the number of bits, it
1234 1.1.8.2 jruoho // wants to be compared against something shifted to have 16;
1235 1.1.8.2 jruoho // that way we don't need to shift inside the loop.
1236 1.1.8.2 jruoho temp = j->code_buffer >> 16;
1237 1.1.8.2 jruoho for (k=FAST_BITS+1 ; ; ++k)
1238 1.1.8.2 jruoho if (temp < h->maxcode[k])
1239 1.1.8.2 jruoho break;
1240 1.1.8.2 jruoho if (k == 17) {
1241 1.1.8.2 jruoho // error! code not found
1242 1.1.8.2 jruoho j->code_bits -= 16;
1243 1.1.8.2 jruoho return -1;
1244 1.1.8.2 jruoho }
1245 1.1.8.2 jruoho
1246 1.1.8.2 jruoho if (k > j->code_bits)
1247 1.1.8.2 jruoho return -1;
1248 1.1.8.2 jruoho
1249 1.1.8.2 jruoho // convert the huffman code to the symbol id
1250 1.1.8.2 jruoho c = ((j->code_buffer >> (32 - k)) & bmask[k]) + h->delta[k];
1251 1.1.8.2 jruoho assert((((j->code_buffer) >> (32 - h->size[c])) & bmask[h->size[c]]) == h->code[c]);
1252 1.1.8.2 jruoho
1253 1.1.8.2 jruoho // convert the id to a symbol
1254 1.1.8.2 jruoho j->code_bits -= k;
1255 1.1.8.2 jruoho j->code_buffer <<= k;
1256 1.1.8.2 jruoho return h->values[c];
1257 1.1.8.2 jruoho }
1258 1.1.8.2 jruoho
1259 1.1.8.2 jruoho // combined JPEG 'receive' and JPEG 'extend', since baseline
1260 1.1.8.2 jruoho // always extends everything it receives.
1261 1.1.8.2 jruoho __forceinline static int extend_receive(jpeg *j, int n)
1262 1.1.8.2 jruoho {
1263 1.1.8.2 jruoho unsigned int m = 1 << (n-1);
1264 1.1.8.2 jruoho unsigned int k;
1265 1.1.8.2 jruoho if (j->code_bits < n) grow_buffer_unsafe(j);
1266 1.1.8.2 jruoho
1267 1.1.8.2 jruoho #if 1
1268 1.1.8.2 jruoho k = stbi_lrot(j->code_buffer, n);
1269 1.1.8.2 jruoho j->code_buffer = k & ~bmask[n];
1270 1.1.8.2 jruoho k &= bmask[n];
1271 1.1.8.2 jruoho j->code_bits -= n;
1272 1.1.8.2 jruoho #else
1273 1.1.8.2 jruoho k = (j->code_buffer >> (32 - n)) & bmask[n];
1274 1.1.8.2 jruoho j->code_bits -= n;
1275 1.1.8.2 jruoho j->code_buffer <<= n;
1276 1.1.8.2 jruoho #endif
1277 1.1.8.2 jruoho // the following test is probably a random branch that won't
1278 1.1.8.2 jruoho // predict well. I tried to table accelerate it but failed.
1279 1.1.8.2 jruoho // maybe it's compiling as a conditional move?
1280 1.1.8.2 jruoho if (k < m)
1281 1.1.8.2 jruoho return (-1 << n) + k + 1;
1282 1.1.8.2 jruoho else
1283 1.1.8.2 jruoho return k;
1284 1.1.8.2 jruoho }
1285 1.1.8.2 jruoho
1286 1.1.8.2 jruoho // given a value that's at position X in the zigzag stream,
1287 1.1.8.2 jruoho // where does it appear in the 8x8 matrix coded as row-major?
1288 1.1.8.2 jruoho static uint8 dezigzag[64+15] =
1289 1.1.8.2 jruoho {
1290 1.1.8.2 jruoho 0, 1, 8, 16, 9, 2, 3, 10,
1291 1.1.8.2 jruoho 17, 24, 32, 25, 18, 11, 4, 5,
1292 1.1.8.2 jruoho 12, 19, 26, 33, 40, 48, 41, 34,
1293 1.1.8.2 jruoho 27, 20, 13, 6, 7, 14, 21, 28,
1294 1.1.8.2 jruoho 35, 42, 49, 56, 57, 50, 43, 36,
1295 1.1.8.2 jruoho 29, 22, 15, 23, 30, 37, 44, 51,
1296 1.1.8.2 jruoho 58, 59, 52, 45, 38, 31, 39, 46,
1297 1.1.8.2 jruoho 53, 60, 61, 54, 47, 55, 62, 63,
1298 1.1.8.2 jruoho // let corrupt input sample past end
1299 1.1.8.2 jruoho 63, 63, 63, 63, 63, 63, 63, 63,
1300 1.1.8.2 jruoho 63, 63, 63, 63, 63, 63, 63
1301 1.1.8.2 jruoho };
1302 1.1.8.2 jruoho
1303 1.1.8.2 jruoho // decode one 64-entry block--
1304 1.1.8.2 jruoho static int decode_block(jpeg *j, short data[64], huffman *hdc, huffman *hac, int b)
1305 1.1.8.2 jruoho {
1306 1.1.8.2 jruoho int diff,dc,k;
1307 1.1.8.2 jruoho int t = decode(j, hdc);
1308 1.1.8.2 jruoho if (t < 0) return e("bad huffman code","Corrupt JPEG");
1309 1.1.8.2 jruoho
1310 1.1.8.2 jruoho // 0 all the ac values now so we can do it 32-bits at a time
1311 1.1.8.2 jruoho memset(data,0,64*sizeof(data[0]));
1312 1.1.8.2 jruoho
1313 1.1.8.2 jruoho diff = t ? extend_receive(j, t) : 0;
1314 1.1.8.2 jruoho dc = j->img_comp[b].dc_pred + diff;
1315 1.1.8.2 jruoho j->img_comp[b].dc_pred = dc;
1316 1.1.8.2 jruoho data[0] = (short) dc;
1317 1.1.8.2 jruoho
1318 1.1.8.2 jruoho // decode AC components, see JPEG spec
1319 1.1.8.2 jruoho k = 1;
1320 1.1.8.2 jruoho do {
1321 1.1.8.2 jruoho int r,s;
1322 1.1.8.2 jruoho int rs = decode(j, hac);
1323 1.1.8.2 jruoho if (rs < 0) return e("bad huffman code","Corrupt JPEG");
1324 1.1.8.2 jruoho s = rs & 15;
1325 1.1.8.2 jruoho r = rs >> 4;
1326 1.1.8.2 jruoho if (s == 0) {
1327 1.1.8.2 jruoho if (rs != 0xf0) break; // end block
1328 1.1.8.2 jruoho k += 16;
1329 1.1.8.2 jruoho } else {
1330 1.1.8.2 jruoho k += r;
1331 1.1.8.2 jruoho // decode into unzigzag'd location
1332 1.1.8.2 jruoho data[dezigzag[k++]] = (short) extend_receive(j,s);
1333 1.1.8.2 jruoho }
1334 1.1.8.2 jruoho } while (k < 64);
1335 1.1.8.2 jruoho return 1;
1336 1.1.8.2 jruoho }
1337 1.1.8.2 jruoho
1338 1.1.8.2 jruoho // take a -128..127 value and clamp it and convert to 0..255
1339 1.1.8.2 jruoho __forceinline static uint8 clamp(int x)
1340 1.1.8.2 jruoho {
1341 1.1.8.2 jruoho // trick to use a single test to catch both cases
1342 1.1.8.2 jruoho if ((unsigned int) x > 255) {
1343 1.1.8.2 jruoho if (x < 0) return 0;
1344 1.1.8.2 jruoho if (x > 255) return 255;
1345 1.1.8.2 jruoho }
1346 1.1.8.2 jruoho return (uint8) x;
1347 1.1.8.2 jruoho }
1348 1.1.8.2 jruoho
1349 1.1.8.2 jruoho #define f2f(x) (int) (((x) * 4096 + 0.5))
1350 1.1.8.2 jruoho #define fsh(x) ((x) << 12)
1351 1.1.8.2 jruoho
1352 1.1.8.2 jruoho // derived from jidctint -- DCT_ISLOW
1353 1.1.8.2 jruoho #define IDCT_1D(s0,s1,s2,s3,s4,s5,s6,s7) \
1354 1.1.8.2 jruoho int t0,t1,t2,t3,p1,p2,p3,p4,p5,x0,x1,x2,x3; \
1355 1.1.8.2 jruoho p2 = s2; \
1356 1.1.8.2 jruoho p3 = s6; \
1357 1.1.8.2 jruoho p1 = (p2+p3) * f2f(0.5411961f); \
1358 1.1.8.2 jruoho t2 = p1 + p3*f2f(-1.847759065f); \
1359 1.1.8.2 jruoho t3 = p1 + p2*f2f( 0.765366865f); \
1360 1.1.8.2 jruoho p2 = s0; \
1361 1.1.8.2 jruoho p3 = s4; \
1362 1.1.8.2 jruoho t0 = fsh(p2+p3); \
1363 1.1.8.2 jruoho t1 = fsh(p2-p3); \
1364 1.1.8.2 jruoho x0 = t0+t3; \
1365 1.1.8.2 jruoho x3 = t0-t3; \
1366 1.1.8.2 jruoho x1 = t1+t2; \
1367 1.1.8.2 jruoho x2 = t1-t2; \
1368 1.1.8.2 jruoho t0 = s7; \
1369 1.1.8.2 jruoho t1 = s5; \
1370 1.1.8.2 jruoho t2 = s3; \
1371 1.1.8.2 jruoho t3 = s1; \
1372 1.1.8.2 jruoho p3 = t0+t2; \
1373 1.1.8.2 jruoho p4 = t1+t3; \
1374 1.1.8.2 jruoho p1 = t0+t3; \
1375 1.1.8.2 jruoho p2 = t1+t2; \
1376 1.1.8.2 jruoho p5 = (p3+p4)*f2f( 1.175875602f); \
1377 1.1.8.2 jruoho t0 = t0*f2f( 0.298631336f); \
1378 1.1.8.2 jruoho t1 = t1*f2f( 2.053119869f); \
1379 1.1.8.2 jruoho t2 = t2*f2f( 3.072711026f); \
1380 1.1.8.2 jruoho t3 = t3*f2f( 1.501321110f); \
1381 1.1.8.2 jruoho p1 = p5 + p1*f2f(-0.899976223f); \
1382 1.1.8.2 jruoho p2 = p5 + p2*f2f(-2.562915447f); \
1383 1.1.8.2 jruoho p3 = p3*f2f(-1.961570560f); \
1384 1.1.8.2 jruoho p4 = p4*f2f(-0.390180644f); \
1385 1.1.8.2 jruoho t3 += p1+p4; \
1386 1.1.8.2 jruoho t2 += p2+p3; \
1387 1.1.8.2 jruoho t1 += p2+p4; \
1388 1.1.8.2 jruoho t0 += p1+p3;
1389 1.1.8.2 jruoho
1390 1.1.8.2 jruoho #ifdef STBI_SIMD
1391 1.1.8.2 jruoho typedef unsigned short stbi_dequantize_t;
1392 1.1.8.2 jruoho #else
1393 1.1.8.2 jruoho typedef uint8 stbi_dequantize_t;
1394 1.1.8.2 jruoho #endif
1395 1.1.8.2 jruoho
1396 1.1.8.2 jruoho // .344 seconds on 3*anemones.jpg
1397 1.1.8.2 jruoho static void idct_block(uint8 *out, int out_stride, short data[64], stbi_dequantize_t *dequantize)
1398 1.1.8.2 jruoho {
1399 1.1.8.2 jruoho int i,val[64],*v=val;
1400 1.1.8.2 jruoho stbi_dequantize_t *dq = dequantize;
1401 1.1.8.2 jruoho uint8 *o;
1402 1.1.8.2 jruoho short *d = data;
1403 1.1.8.2 jruoho
1404 1.1.8.2 jruoho // columns
1405 1.1.8.2 jruoho for (i=0; i < 8; ++i,++d,++dq, ++v) {
1406 1.1.8.2 jruoho // if all zeroes, shortcut -- this avoids dequantizing 0s and IDCTing
1407 1.1.8.2 jruoho if (d[ 8]==0 && d[16]==0 && d[24]==0 && d[32]==0
1408 1.1.8.2 jruoho && d[40]==0 && d[48]==0 && d[56]==0) {
1409 1.1.8.2 jruoho // no shortcut 0 seconds
1410 1.1.8.2 jruoho // (1|2|3|4|5|6|7)==0 0 seconds
1411 1.1.8.2 jruoho // all separate -0.047 seconds
1412 1.1.8.2 jruoho // 1 && 2|3 && 4|5 && 6|7: -0.047 seconds
1413 1.1.8.2 jruoho int dcterm = d[0] * dq[0] << 2;
1414 1.1.8.2 jruoho v[0] = v[8] = v[16] = v[24] = v[32] = v[40] = v[48] = v[56] = dcterm;
1415 1.1.8.2 jruoho } else {
1416 1.1.8.2 jruoho IDCT_1D(d[ 0]*dq[ 0],d[ 8]*dq[ 8],d[16]*dq[16],d[24]*dq[24],
1417 1.1.8.2 jruoho d[32]*dq[32],d[40]*dq[40],d[48]*dq[48],d[56]*dq[56])
1418 1.1.8.2 jruoho // constants scaled things up by 1<<12; let's bring them back
1419 1.1.8.2 jruoho // down, but keep 2 extra bits of precision
1420 1.1.8.2 jruoho x0 += 512; x1 += 512; x2 += 512; x3 += 512;
1421 1.1.8.2 jruoho v[ 0] = (x0+t3) >> 10;
1422 1.1.8.2 jruoho v[56] = (x0-t3) >> 10;
1423 1.1.8.2 jruoho v[ 8] = (x1+t2) >> 10;
1424 1.1.8.2 jruoho v[48] = (x1-t2) >> 10;
1425 1.1.8.2 jruoho v[16] = (x2+t1) >> 10;
1426 1.1.8.2 jruoho v[40] = (x2-t1) >> 10;
1427 1.1.8.2 jruoho v[24] = (x3+t0) >> 10;
1428 1.1.8.2 jruoho v[32] = (x3-t0) >> 10;
1429 1.1.8.2 jruoho }
1430 1.1.8.2 jruoho }
1431 1.1.8.2 jruoho
1432 1.1.8.2 jruoho for (i=0, v=val, o=out; i < 8; ++i,v+=8,o+=out_stride) {
1433 1.1.8.2 jruoho // no fast case since the first 1D IDCT spread components out
1434 1.1.8.2 jruoho IDCT_1D(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7])
1435 1.1.8.2 jruoho // constants scaled things up by 1<<12, plus we had 1<<2 from first
1436 1.1.8.2 jruoho // loop, plus horizontal and vertical each scale by sqrt(8) so together
1437 1.1.8.2 jruoho // we've got an extra 1<<3, so 1<<17 total we need to remove.
1438 1.1.8.2 jruoho // so we want to round that, which means adding 0.5 * 1<<17,
1439 1.1.8.2 jruoho // aka 65536. Also, we'll end up with -128 to 127 that we want
1440 1.1.8.2 jruoho // to encode as 0..255 by adding 128, so we'll add that before the shift
1441 1.1.8.2 jruoho x0 += 65536 + (128<<17);
1442 1.1.8.2 jruoho x1 += 65536 + (128<<17);
1443 1.1.8.2 jruoho x2 += 65536 + (128<<17);
1444 1.1.8.2 jruoho x3 += 65536 + (128<<17);
1445 1.1.8.2 jruoho // tried computing the shifts into temps, or'ing the temps to see
1446 1.1.8.2 jruoho // if any were out of range, but that was slower
1447 1.1.8.2 jruoho o[0] = clamp((x0+t3) >> 17);
1448 1.1.8.2 jruoho o[7] = clamp((x0-t3) >> 17);
1449 1.1.8.2 jruoho o[1] = clamp((x1+t2) >> 17);
1450 1.1.8.2 jruoho o[6] = clamp((x1-t2) >> 17);
1451 1.1.8.2 jruoho o[2] = clamp((x2+t1) >> 17);
1452 1.1.8.2 jruoho o[5] = clamp((x2-t1) >> 17);
1453 1.1.8.2 jruoho o[3] = clamp((x3+t0) >> 17);
1454 1.1.8.2 jruoho o[4] = clamp((x3-t0) >> 17);
1455 1.1.8.2 jruoho }
1456 1.1.8.2 jruoho }
1457 1.1.8.2 jruoho
1458 1.1.8.2 jruoho #ifdef STBI_SIMD
1459 1.1.8.2 jruoho static stbi_idct_8x8 stbi_idct_installed = idct_block;
1460 1.1.8.2 jruoho
1461 1.1.8.2 jruoho extern void stbi_install_idct(stbi_idct_8x8 func)
1462 1.1.8.2 jruoho {
1463 1.1.8.2 jruoho stbi_idct_installed = func;
1464 1.1.8.2 jruoho }
1465 1.1.8.2 jruoho #endif
1466 1.1.8.2 jruoho
1467 1.1.8.2 jruoho #define MARKER_none 0xff
1468 1.1.8.2 jruoho // if there's a pending marker from the entropy stream, return that
1469 1.1.8.2 jruoho // otherwise, fetch from the stream and get a marker. if there's no
1470 1.1.8.2 jruoho // marker, return 0xff, which is never a valid marker value
1471 1.1.8.2 jruoho static uint8 get_marker(jpeg *j)
1472 1.1.8.2 jruoho {
1473 1.1.8.2 jruoho uint8 x;
1474 1.1.8.2 jruoho if (j->marker != MARKER_none) { x = j->marker; j->marker = MARKER_none; return x; }
1475 1.1.8.2 jruoho x = get8u(&j->s);
1476 1.1.8.2 jruoho if (x != 0xff) return MARKER_none;
1477 1.1.8.2 jruoho while (x == 0xff)
1478 1.1.8.2 jruoho x = get8u(&j->s);
1479 1.1.8.2 jruoho return x;
1480 1.1.8.2 jruoho }
1481 1.1.8.2 jruoho
1482 1.1.8.2 jruoho // in each scan, we'll have scan_n components, and the order
1483 1.1.8.2 jruoho // of the components is specified by order[]
1484 1.1.8.2 jruoho #define RESTART(x) ((x) >= 0xd0 && (x) <= 0xd7)
1485 1.1.8.2 jruoho
1486 1.1.8.2 jruoho // after a restart interval, reset the entropy decoder and
1487 1.1.8.2 jruoho // the dc prediction
1488 1.1.8.2 jruoho static void reset(jpeg *j)
1489 1.1.8.2 jruoho {
1490 1.1.8.2 jruoho j->code_bits = 0;
1491 1.1.8.2 jruoho j->code_buffer = 0;
1492 1.1.8.2 jruoho j->nomore = 0;
1493 1.1.8.2 jruoho j->img_comp[0].dc_pred = j->img_comp[1].dc_pred = j->img_comp[2].dc_pred = 0;
1494 1.1.8.2 jruoho j->marker = MARKER_none;
1495 1.1.8.2 jruoho j->todo = j->restart_interval ? j->restart_interval : 0x7fffffff;
1496 1.1.8.2 jruoho // no more than 1<<31 MCUs if no restart_interal? that's plenty safe,
1497 1.1.8.2 jruoho // since we don't even allow 1<<30 pixels
1498 1.1.8.2 jruoho }
1499 1.1.8.2 jruoho
1500 1.1.8.2 jruoho static int parse_entropy_coded_data(jpeg *z)
1501 1.1.8.2 jruoho {
1502 1.1.8.2 jruoho reset(z);
1503 1.1.8.2 jruoho if (z->scan_n == 1) {
1504 1.1.8.2 jruoho int i,j;
1505 1.1.8.2 jruoho #ifdef STBI_SIMD
1506 1.1.8.2 jruoho __declspec(align(16))
1507 1.1.8.2 jruoho #endif
1508 1.1.8.2 jruoho short data[64];
1509 1.1.8.2 jruoho int n = z->order[0];
1510 1.1.8.2 jruoho // non-interleaved data, we just need to process one block at a time,
1511 1.1.8.2 jruoho // in trivial scanline order
1512 1.1.8.2 jruoho // number of blocks to do just depends on how many actual "pixels" this
1513 1.1.8.2 jruoho // component has, independent of interleaved MCU blocking and such
1514 1.1.8.2 jruoho int w = (z->img_comp[n].x+7) >> 3;
1515 1.1.8.2 jruoho int h = (z->img_comp[n].y+7) >> 3;
1516 1.1.8.2 jruoho for (j=0; j < h; ++j) {
1517 1.1.8.2 jruoho for (i=0; i < w; ++i) {
1518 1.1.8.2 jruoho if (!decode_block(z, data, z->huff_dc+z->img_comp[n].hd, z->huff_ac+z->img_comp[n].ha, n)) return 0;
1519 1.1.8.2 jruoho #ifdef STBI_SIMD
1520 1.1.8.2 jruoho stbi_idct_installed(z->img_comp[n].data+z->img_comp[n].w2*j*8+i*8, z->img_comp[n].w2, data, z->dequant2[z->img_comp[n].tq]);
1521 1.1.8.2 jruoho #else
1522 1.1.8.2 jruoho idct_block(z->img_comp[n].data+z->img_comp[n].w2*j*8+i*8, z->img_comp[n].w2, data, z->dequant[z->img_comp[n].tq]);
1523 1.1.8.2 jruoho #endif
1524 1.1.8.2 jruoho // every data block is an MCU, so countdown the restart interval
1525 1.1.8.2 jruoho if (--z->todo <= 0) {
1526 1.1.8.2 jruoho if (z->code_bits < 24) grow_buffer_unsafe(z);
1527 1.1.8.2 jruoho // if it's NOT a restart, then just bail, so we get corrupt data
1528 1.1.8.2 jruoho // rather than no data
1529 1.1.8.2 jruoho if (!RESTART(z->marker)) return 1;
1530 1.1.8.2 jruoho reset(z);
1531 1.1.8.2 jruoho }
1532 1.1.8.2 jruoho }
1533 1.1.8.2 jruoho }
1534 1.1.8.2 jruoho } else { // interleaved!
1535 1.1.8.2 jruoho int i,j,k,x,y;
1536 1.1.8.2 jruoho short data[64];
1537 1.1.8.2 jruoho for (j=0; j < z->img_mcu_y; ++j) {
1538 1.1.8.2 jruoho for (i=0; i < z->img_mcu_x; ++i) {
1539 1.1.8.2 jruoho // scan an interleaved mcu... process scan_n components in order
1540 1.1.8.2 jruoho for (k=0; k < z->scan_n; ++k) {
1541 1.1.8.2 jruoho int n = z->order[k];
1542 1.1.8.2 jruoho // scan out an mcu's worth of this component; that's just determined
1543 1.1.8.2 jruoho // by the basic H and V specified for the component
1544 1.1.8.2 jruoho for (y=0; y < z->img_comp[n].v; ++y) {
1545 1.1.8.2 jruoho for (x=0; x < z->img_comp[n].h; ++x) {
1546 1.1.8.2 jruoho int x2 = (i*z->img_comp[n].h + x)*8;
1547 1.1.8.2 jruoho int y2 = (j*z->img_comp[n].v + y)*8;
1548 1.1.8.2 jruoho if (!decode_block(z, data, z->huff_dc+z->img_comp[n].hd, z->huff_ac+z->img_comp[n].ha, n)) return 0;
1549 1.1.8.2 jruoho #ifdef STBI_SIMD
1550 1.1.8.2 jruoho stbi_idct_installed(z->img_comp[n].data+z->img_comp[n].w2*y2+x2, z->img_comp[n].w2, data, z->dequant2[z->img_comp[n].tq]);
1551 1.1.8.2 jruoho #else
1552 1.1.8.2 jruoho idct_block(z->img_comp[n].data+z->img_comp[n].w2*y2+x2, z->img_comp[n].w2, data, z->dequant[z->img_comp[n].tq]);
1553 1.1.8.2 jruoho #endif
1554 1.1.8.2 jruoho }
1555 1.1.8.2 jruoho }
1556 1.1.8.2 jruoho }
1557 1.1.8.2 jruoho // after all interleaved components, that's an interleaved MCU,
1558 1.1.8.2 jruoho // so now count down the restart interval
1559 1.1.8.2 jruoho if (--z->todo <= 0) {
1560 1.1.8.2 jruoho if (z->code_bits < 24) grow_buffer_unsafe(z);
1561 1.1.8.2 jruoho // if it's NOT a restart, then just bail, so we get corrupt data
1562 1.1.8.2 jruoho // rather than no data
1563 1.1.8.2 jruoho if (!RESTART(z->marker)) return 1;
1564 1.1.8.2 jruoho reset(z);
1565 1.1.8.2 jruoho }
1566 1.1.8.2 jruoho }
1567 1.1.8.2 jruoho }
1568 1.1.8.2 jruoho }
1569 1.1.8.2 jruoho return 1;
1570 1.1.8.2 jruoho }
1571 1.1.8.2 jruoho
1572 1.1.8.2 jruoho static int process_marker(jpeg *z, int marker)
1573 1.1.8.2 jruoho {
1574 1.1.8.2 jruoho int L;
1575 1.1.8.2 jruoho switch (marker) {
1576 1.1.8.2 jruoho case MARKER_none: // no marker found
1577 1.1.8.2 jruoho return e("expected marker","Corrupt JPEG");
1578 1.1.8.2 jruoho
1579 1.1.8.2 jruoho case 0xC2: // SOF - progressive
1580 1.1.8.2 jruoho return e("progressive jpeg","JPEG format not supported (progressive)");
1581 1.1.8.2 jruoho
1582 1.1.8.2 jruoho case 0xDD: // DRI - specify restart interval
1583 1.1.8.2 jruoho if (get16(&z->s) != 4) return e("bad DRI len","Corrupt JPEG");
1584 1.1.8.2 jruoho z->restart_interval = get16(&z->s);
1585 1.1.8.2 jruoho return 1;
1586 1.1.8.2 jruoho
1587 1.1.8.2 jruoho case 0xDB: // DQT - define quantization table
1588 1.1.8.2 jruoho L = get16(&z->s)-2;
1589 1.1.8.2 jruoho while (L > 0) {
1590 1.1.8.2 jruoho int q = get8(&z->s);
1591 1.1.8.2 jruoho int p = q >> 4;
1592 1.1.8.2 jruoho int t = q & 15,i;
1593 1.1.8.2 jruoho if (p != 0) return e("bad DQT type","Corrupt JPEG");
1594 1.1.8.2 jruoho if (t > 3) return e("bad DQT table","Corrupt JPEG");
1595 1.1.8.2 jruoho for (i=0; i < 64; ++i)
1596 1.1.8.2 jruoho z->dequant[t][dezigzag[i]] = get8u(&z->s);
1597 1.1.8.2 jruoho #ifdef STBI_SIMD
1598 1.1.8.2 jruoho for (i=0; i < 64; ++i)
1599 1.1.8.2 jruoho z->dequant2[t][i] = z->dequant[t][i];
1600 1.1.8.2 jruoho #endif
1601 1.1.8.2 jruoho L -= 65;
1602 1.1.8.2 jruoho }
1603 1.1.8.2 jruoho return L==0;
1604 1.1.8.2 jruoho
1605 1.1.8.2 jruoho case 0xC4: // DHT - define huffman table
1606 1.1.8.2 jruoho L = get16(&z->s)-2;
1607 1.1.8.2 jruoho while (L > 0) {
1608 1.1.8.2 jruoho uint8 *v;
1609 1.1.8.2 jruoho int sizes[16],i,m=0;
1610 1.1.8.2 jruoho int q = get8(&z->s);
1611 1.1.8.2 jruoho int tc = q >> 4;
1612 1.1.8.2 jruoho int th = q & 15;
1613 1.1.8.2 jruoho if (tc > 1 || th > 3) return e("bad DHT header","Corrupt JPEG");
1614 1.1.8.2 jruoho for (i=0; i < 16; ++i) {
1615 1.1.8.2 jruoho sizes[i] = get8(&z->s);
1616 1.1.8.2 jruoho m += sizes[i];
1617 1.1.8.2 jruoho }
1618 1.1.8.2 jruoho L -= 17;
1619 1.1.8.2 jruoho if (tc == 0) {
1620 1.1.8.2 jruoho if (!build_huffman(z->huff_dc+th, sizes)) return 0;
1621 1.1.8.2 jruoho v = z->huff_dc[th].values;
1622 1.1.8.2 jruoho } else {
1623 1.1.8.2 jruoho if (!build_huffman(z->huff_ac+th, sizes)) return 0;
1624 1.1.8.2 jruoho v = z->huff_ac[th].values;
1625 1.1.8.2 jruoho }
1626 1.1.8.2 jruoho for (i=0; i < m; ++i)
1627 1.1.8.2 jruoho v[i] = get8u(&z->s);
1628 1.1.8.2 jruoho L -= m;
1629 1.1.8.2 jruoho }
1630 1.1.8.2 jruoho return L==0;
1631 1.1.8.2 jruoho }
1632 1.1.8.2 jruoho // check for comment block or APP blocks
1633 1.1.8.2 jruoho if ((marker >= 0xE0 && marker <= 0xEF) || marker == 0xFE) {
1634 1.1.8.2 jruoho skip(&z->s, get16(&z->s)-2);
1635 1.1.8.2 jruoho return 1;
1636 1.1.8.2 jruoho }
1637 1.1.8.2 jruoho return 0;
1638 1.1.8.2 jruoho }
1639 1.1.8.2 jruoho
1640 1.1.8.2 jruoho // after we see SOS
1641 1.1.8.2 jruoho static int process_scan_header(jpeg *z)
1642 1.1.8.2 jruoho {
1643 1.1.8.2 jruoho int i;
1644 1.1.8.2 jruoho int Ls = get16(&z->s);
1645 1.1.8.2 jruoho z->scan_n = get8(&z->s);
1646 1.1.8.2 jruoho if (z->scan_n < 1 || z->scan_n > 4 || z->scan_n > (int) z->s.img_n) return e("bad SOS component count","Corrupt JPEG");
1647 1.1.8.2 jruoho if (Ls != 6+2*z->scan_n) return e("bad SOS len","Corrupt JPEG");
1648 1.1.8.2 jruoho for (i=0; i < z->scan_n; ++i) {
1649 1.1.8.2 jruoho int id = get8(&z->s), which;
1650 1.1.8.2 jruoho int q = get8(&z->s);
1651 1.1.8.2 jruoho for (which = 0; which < z->s.img_n; ++which)
1652 1.1.8.2 jruoho if (z->img_comp[which].id == id)
1653 1.1.8.2 jruoho break;
1654 1.1.8.2 jruoho if (which == z->s.img_n) return 0;
1655 1.1.8.2 jruoho z->img_comp[which].hd = q >> 4; if (z->img_comp[which].hd > 3) return e("bad DC huff","Corrupt JPEG");
1656 1.1.8.2 jruoho z->img_comp[which].ha = q & 15; if (z->img_comp[which].ha > 3) return e("bad AC huff","Corrupt JPEG");
1657 1.1.8.2 jruoho z->order[i] = which;
1658 1.1.8.2 jruoho }
1659 1.1.8.2 jruoho if (get8(&z->s) != 0) return e("bad SOS","Corrupt JPEG");
1660 1.1.8.2 jruoho get8(&z->s); // should be 63, but might be 0
1661 1.1.8.2 jruoho if (get8(&z->s) != 0) return e("bad SOS","Corrupt JPEG");
1662 1.1.8.2 jruoho
1663 1.1.8.2 jruoho return 1;
1664 1.1.8.2 jruoho }
1665 1.1.8.2 jruoho
1666 1.1.8.2 jruoho static int process_frame_header(jpeg *z, int scan)
1667 1.1.8.2 jruoho {
1668 1.1.8.2 jruoho stbi *s = &z->s;
1669 1.1.8.2 jruoho int Lf,p,i,q, h_max=1,v_max=1,c;
1670 1.1.8.2 jruoho Lf = get16(s); if (Lf < 11) return e("bad SOF len","Corrupt JPEG"); // JPEG
1671 1.1.8.2 jruoho p = get8(s); if (p != 8) return e("only 8-bit","JPEG format not supported: 8-bit only"); // JPEG baseline
1672 1.1.8.2 jruoho s->img_y = get16(s); if (s->img_y == 0) return e("no header height", "JPEG format not supported: delayed height"); // Legal, but we don't handle it--but neither does IJG
1673 1.1.8.2 jruoho s->img_x = get16(s); if (s->img_x == 0) return e("0 width","Corrupt JPEG"); // JPEG requires
1674 1.1.8.2 jruoho c = get8(s);
1675 1.1.8.2 jruoho if (c != 3 && c != 1) return e("bad component count","Corrupt JPEG"); // JFIF requires
1676 1.1.8.2 jruoho s->img_n = c;
1677 1.1.8.2 jruoho for (i=0; i < c; ++i) {
1678 1.1.8.2 jruoho z->img_comp[i].data = NULL;
1679 1.1.8.2 jruoho z->img_comp[i].linebuf = NULL;
1680 1.1.8.2 jruoho }
1681 1.1.8.2 jruoho
1682 1.1.8.2 jruoho if (Lf != 8+3*s->img_n) return e("bad SOF len","Corrupt JPEG");
1683 1.1.8.2 jruoho
1684 1.1.8.2 jruoho for (i=0; i < s->img_n; ++i) {
1685 1.1.8.2 jruoho z->img_comp[i].id = get8(s);
1686 1.1.8.2 jruoho if (z->img_comp[i].id != i+1) // JFIF requires
1687 1.1.8.2 jruoho if (z->img_comp[i].id != i) // some version of jpegtran outputs non-JFIF-compliant files!
1688 1.1.8.2 jruoho return e("bad component ID","Corrupt JPEG");
1689 1.1.8.2 jruoho q = get8(s);
1690 1.1.8.2 jruoho z->img_comp[i].h = (q >> 4); if (!z->img_comp[i].h || z->img_comp[i].h > 4) return e("bad H","Corrupt JPEG");
1691 1.1.8.2 jruoho z->img_comp[i].v = q & 15; if (!z->img_comp[i].v || z->img_comp[i].v > 4) return e("bad V","Corrupt JPEG");
1692 1.1.8.2 jruoho z->img_comp[i].tq = get8(s); if (z->img_comp[i].tq > 3) return e("bad TQ","Corrupt JPEG");
1693 1.1.8.2 jruoho }
1694 1.1.8.2 jruoho
1695 1.1.8.2 jruoho if (scan != SCAN_load) return 1;
1696 1.1.8.2 jruoho
1697 1.1.8.2 jruoho if ((1 << 30) / s->img_x / s->img_n < s->img_y) return e("too large", "Image too large to decode");
1698 1.1.8.2 jruoho
1699 1.1.8.2 jruoho for (i=0; i < s->img_n; ++i) {
1700 1.1.8.2 jruoho if (z->img_comp[i].h > h_max) h_max = z->img_comp[i].h;
1701 1.1.8.2 jruoho if (z->img_comp[i].v > v_max) v_max = z->img_comp[i].v;
1702 1.1.8.2 jruoho }
1703 1.1.8.2 jruoho
1704 1.1.8.2 jruoho // compute interleaved mcu info
1705 1.1.8.2 jruoho z->img_h_max = h_max;
1706 1.1.8.2 jruoho z->img_v_max = v_max;
1707 1.1.8.2 jruoho z->img_mcu_w = h_max * 8;
1708 1.1.8.2 jruoho z->img_mcu_h = v_max * 8;
1709 1.1.8.2 jruoho z->img_mcu_x = (s->img_x + z->img_mcu_w-1) / z->img_mcu_w;
1710 1.1.8.2 jruoho z->img_mcu_y = (s->img_y + z->img_mcu_h-1) / z->img_mcu_h;
1711 1.1.8.2 jruoho
1712 1.1.8.2 jruoho for (i=0; i < s->img_n; ++i) {
1713 1.1.8.2 jruoho // number of effective pixels (e.g. for non-interleaved MCU)
1714 1.1.8.2 jruoho z->img_comp[i].x = (s->img_x * z->img_comp[i].h + h_max-1) / h_max;
1715 1.1.8.2 jruoho z->img_comp[i].y = (s->img_y * z->img_comp[i].v + v_max-1) / v_max;
1716 1.1.8.2 jruoho // to simplify generation, we'll allocate enough memory to decode
1717 1.1.8.2 jruoho // the bogus oversized data from using interleaved MCUs and their
1718 1.1.8.2 jruoho // big blocks (e.g. a 16x16 iMCU on an image of width 33); we won't
1719 1.1.8.2 jruoho // discard the extra data until colorspace conversion
1720 1.1.8.2 jruoho z->img_comp[i].w2 = z->img_mcu_x * z->img_comp[i].h * 8;
1721 1.1.8.2 jruoho z->img_comp[i].h2 = z->img_mcu_y * z->img_comp[i].v * 8;
1722 1.1.8.2 jruoho z->img_comp[i].raw_data = MALLOC(z->img_comp[i].w2 * z->img_comp[i].h2+15);
1723 1.1.8.2 jruoho if (z->img_comp[i].raw_data == NULL) {
1724 1.1.8.2 jruoho for(--i; i >= 0; --i) {
1725 1.1.8.2 jruoho FREE(z->img_comp[i].raw_data);
1726 1.1.8.2 jruoho z->img_comp[i].data = NULL;
1727 1.1.8.2 jruoho }
1728 1.1.8.2 jruoho return e("outofmem", "Out of memory");
1729 1.1.8.2 jruoho }
1730 1.1.8.2 jruoho // align blocks for installable-idct using mmx/sse
1731 1.1.8.2 jruoho z->img_comp[i].data = (uint8*) (((size_t) z->img_comp[i].raw_data + 15) & ~15);
1732 1.1.8.2 jruoho z->img_comp[i].linebuf = NULL;
1733 1.1.8.2 jruoho }
1734 1.1.8.2 jruoho
1735 1.1.8.2 jruoho return 1;
1736 1.1.8.2 jruoho }
1737 1.1.8.2 jruoho
1738 1.1.8.2 jruoho // use comparisons since in some cases we handle more than one case (e.g. SOF)
1739 1.1.8.2 jruoho #define DNL(x) ((x) == 0xdc)
1740 1.1.8.2 jruoho #define SOI(x) ((x) == 0xd8)
1741 1.1.8.2 jruoho #define EOI(x) ((x) == 0xd9)
1742 1.1.8.2 jruoho #define SOF(x) ((x) == 0xc0 || (x) == 0xc1)
1743 1.1.8.2 jruoho #define SOS(x) ((x) == 0xda)
1744 1.1.8.2 jruoho
1745 1.1.8.2 jruoho static int decode_jpeg_header(jpeg *z, int scan)
1746 1.1.8.2 jruoho {
1747 1.1.8.2 jruoho int m;
1748 1.1.8.2 jruoho z->marker = MARKER_none; // initialize cached marker to empty
1749 1.1.8.2 jruoho m = get_marker(z);
1750 1.1.8.2 jruoho if (!SOI(m)) return e("no SOI","Corrupt JPEG");
1751 1.1.8.2 jruoho if (scan == SCAN_type) return 1;
1752 1.1.8.2 jruoho m = get_marker(z);
1753 1.1.8.2 jruoho while (!SOF(m)) {
1754 1.1.8.2 jruoho if (!process_marker(z,m)) return 0;
1755 1.1.8.2 jruoho m = get_marker(z);
1756 1.1.8.2 jruoho while (m == MARKER_none) {
1757 1.1.8.2 jruoho // some files have extra padding after their blocks, so ok, we'll scan
1758 1.1.8.2 jruoho if (at_eof(&z->s)) return e("no SOF", "Corrupt JPEG");
1759 1.1.8.2 jruoho m = get_marker(z);
1760 1.1.8.2 jruoho }
1761 1.1.8.2 jruoho }
1762 1.1.8.2 jruoho if (!process_frame_header(z, scan)) return 0;
1763 1.1.8.2 jruoho return 1;
1764 1.1.8.2 jruoho }
1765 1.1.8.2 jruoho
1766 1.1.8.2 jruoho static int decode_jpeg_image(jpeg *j)
1767 1.1.8.2 jruoho {
1768 1.1.8.2 jruoho int m;
1769 1.1.8.2 jruoho j->restart_interval = 0;
1770 1.1.8.2 jruoho if (!decode_jpeg_header(j, SCAN_load)) return 0;
1771 1.1.8.2 jruoho m = get_marker(j);
1772 1.1.8.2 jruoho while (!EOI(m)) {
1773 1.1.8.2 jruoho if (SOS(m)) {
1774 1.1.8.2 jruoho if (!process_scan_header(j)) return 0;
1775 1.1.8.2 jruoho if (!parse_entropy_coded_data(j)) return 0;
1776 1.1.8.2 jruoho if (j->marker == MARKER_none ) {
1777 1.1.8.2 jruoho // handle 0s at the end of image data from IP Kamera 9060
1778 1.1.8.2 jruoho while (!at_eof(&j->s)) {
1779 1.1.8.2 jruoho int x = get8(&j->s);
1780 1.1.8.2 jruoho if (x == 255) {
1781 1.1.8.2 jruoho j->marker = get8u(&j->s);
1782 1.1.8.2 jruoho break;
1783 1.1.8.2 jruoho } else if (x != 0) {
1784 1.1.8.2 jruoho return 0;
1785 1.1.8.2 jruoho }
1786 1.1.8.2 jruoho }
1787 1.1.8.2 jruoho // if we reach eof without hitting a marker, get_marker() below will fail and we'll eventually return 0
1788 1.1.8.2 jruoho }
1789 1.1.8.2 jruoho } else {
1790 1.1.8.2 jruoho if (!process_marker(j, m)) return 0;
1791 1.1.8.2 jruoho }
1792 1.1.8.2 jruoho m = get_marker(j);
1793 1.1.8.2 jruoho }
1794 1.1.8.2 jruoho return 1;
1795 1.1.8.2 jruoho }
1796 1.1.8.2 jruoho
1797 1.1.8.2 jruoho // static jfif-centered resampling (across block boundaries)
1798 1.1.8.2 jruoho
1799 1.1.8.2 jruoho typedef uint8 *(*resample_row_func)(uint8 *out, uint8 *in0, uint8 *in1,
1800 1.1.8.2 jruoho int w, int hs);
1801 1.1.8.2 jruoho
1802 1.1.8.2 jruoho #define div4(x) ((uint8) ((x) >> 2))
1803 1.1.8.2 jruoho
1804 1.1.8.2 jruoho static uint8 *resample_row_1(uint8 *out, uint8 *in_near, uint8 *in_far, int w, int hs)
1805 1.1.8.2 jruoho {
1806 1.1.8.2 jruoho STBI_NOTUSED(out);
1807 1.1.8.2 jruoho STBI_NOTUSED(in_far);
1808 1.1.8.2 jruoho STBI_NOTUSED(w);
1809 1.1.8.2 jruoho STBI_NOTUSED(hs);
1810 1.1.8.2 jruoho return in_near;
1811 1.1.8.2 jruoho }
1812 1.1.8.2 jruoho
1813 1.1.8.2 jruoho static uint8* resample_row_v_2(uint8 *out, uint8 *in_near, uint8 *in_far, int w, int hs)
1814 1.1.8.2 jruoho {
1815 1.1.8.2 jruoho // need to generate two samples vertically for every one in input
1816 1.1.8.2 jruoho int i;
1817 1.1.8.2 jruoho STBI_NOTUSED(hs);
1818 1.1.8.2 jruoho for (i=0; i < w; ++i)
1819 1.1.8.2 jruoho out[i] = div4(3*in_near[i] + in_far[i] + 2);
1820 1.1.8.2 jruoho return out;
1821 1.1.8.2 jruoho }
1822 1.1.8.2 jruoho
1823 1.1.8.2 jruoho static uint8* resample_row_h_2(uint8 *out, uint8 *in_near, uint8 *in_far, int w, int hs)
1824 1.1.8.2 jruoho {
1825 1.1.8.2 jruoho // need to generate two samples horizontally for every one in input
1826 1.1.8.2 jruoho int i;
1827 1.1.8.2 jruoho uint8 *input = in_near;
1828 1.1.8.2 jruoho
1829 1.1.8.2 jruoho if (w == 1) {
1830 1.1.8.2 jruoho // if only one sample, can't do any interpolation
1831 1.1.8.2 jruoho out[0] = out[1] = input[0];
1832 1.1.8.2 jruoho return out;
1833 1.1.8.2 jruoho }
1834 1.1.8.2 jruoho
1835 1.1.8.2 jruoho out[0] = input[0];
1836 1.1.8.2 jruoho out[1] = div4(input[0]*3 + input[1] + 2);
1837 1.1.8.2 jruoho for (i=1; i < w-1; ++i) {
1838 1.1.8.2 jruoho int n = 3*input[i]+2;
1839 1.1.8.2 jruoho out[i*2+0] = div4(n+input[i-1]);
1840 1.1.8.2 jruoho out[i*2+1] = div4(n+input[i+1]);
1841 1.1.8.2 jruoho }
1842 1.1.8.2 jruoho out[i*2+0] = div4(input[w-2]*3 + input[w-1] + 2);
1843 1.1.8.2 jruoho out[i*2+1] = input[w-1];
1844 1.1.8.2 jruoho
1845 1.1.8.2 jruoho STBI_NOTUSED(in_far);
1846 1.1.8.2 jruoho STBI_NOTUSED(hs);
1847 1.1.8.2 jruoho
1848 1.1.8.2 jruoho return out;
1849 1.1.8.2 jruoho }
1850 1.1.8.2 jruoho
1851 1.1.8.2 jruoho #define div16(x) ((uint8) ((x) >> 4))
1852 1.1.8.2 jruoho
1853 1.1.8.2 jruoho static uint8 *resample_row_hv_2(uint8 *out, uint8 *in_near, uint8 *in_far, int w, int hs)
1854 1.1.8.2 jruoho {
1855 1.1.8.2 jruoho // need to generate 2x2 samples for every one in input
1856 1.1.8.2 jruoho int i,t0,t1;
1857 1.1.8.2 jruoho if (w == 1) {
1858 1.1.8.2 jruoho out[0] = out[1] = div4(3*in_near[0] + in_far[0] + 2);
1859 1.1.8.2 jruoho return out;
1860 1.1.8.2 jruoho }
1861 1.1.8.2 jruoho
1862 1.1.8.2 jruoho t1 = 3*in_near[0] + in_far[0];
1863 1.1.8.2 jruoho out[0] = div4(t1+2);
1864 1.1.8.2 jruoho for (i=1; i < w; ++i) {
1865 1.1.8.2 jruoho t0 = t1;
1866 1.1.8.2 jruoho t1 = 3*in_near[i]+in_far[i];
1867 1.1.8.2 jruoho out[i*2-1] = div16(3*t0 + t1 + 8);
1868 1.1.8.2 jruoho out[i*2 ] = div16(3*t1 + t0 + 8);
1869 1.1.8.2 jruoho }
1870 1.1.8.2 jruoho out[w*2-1] = div4(t1+2);
1871 1.1.8.2 jruoho
1872 1.1.8.2 jruoho STBI_NOTUSED(hs);
1873 1.1.8.2 jruoho
1874 1.1.8.2 jruoho return out;
1875 1.1.8.2 jruoho }
1876 1.1.8.2 jruoho
1877 1.1.8.2 jruoho static uint8 *resample_row_generic(uint8 *out, uint8 *in_near, uint8 *in_far, int w, int hs)
1878 1.1.8.2 jruoho {
1879 1.1.8.2 jruoho // resample with nearest-neighbor
1880 1.1.8.2 jruoho int i,j;
1881 1.1.8.2 jruoho in_far = in_far;
1882 1.1.8.2 jruoho for (i=0; i < w; ++i)
1883 1.1.8.2 jruoho for (j=0; j < hs; ++j)
1884 1.1.8.2 jruoho out[i*hs+j] = in_near[i];
1885 1.1.8.2 jruoho return out;
1886 1.1.8.2 jruoho }
1887 1.1.8.2 jruoho
1888 1.1.8.2 jruoho #define float2fixed(x) ((int) ((x) * 65536 + 0.5))
1889 1.1.8.2 jruoho
1890 1.1.8.2 jruoho // 0.38 seconds on 3*anemones.jpg (0.25 with processor = Pro)
1891 1.1.8.2 jruoho // VC6 without processor=Pro is generating multiple LEAs per multiply!
1892 1.1.8.2 jruoho static void YCbCr_to_RGB_row(uint8 *out, const uint8 *y, const uint8 *pcb, const uint8 *pcr, int count, int step)
1893 1.1.8.2 jruoho {
1894 1.1.8.2 jruoho int i;
1895 1.1.8.2 jruoho for (i=0; i < count; ++i) {
1896 1.1.8.2 jruoho int y_fixed = (y[i] << 16) + 32768; // rounding
1897 1.1.8.2 jruoho int r,g,b;
1898 1.1.8.2 jruoho int cr = pcr[i] - 128;
1899 1.1.8.2 jruoho int cb = pcb[i] - 128;
1900 1.1.8.2 jruoho r = y_fixed + cr*float2fixed(1.40200f);
1901 1.1.8.2 jruoho g = y_fixed - cr*float2fixed(0.71414f) - cb*float2fixed(0.34414f);
1902 1.1.8.2 jruoho b = y_fixed + cb*float2fixed(1.77200f);
1903 1.1.8.2 jruoho r >>= 16;
1904 1.1.8.2 jruoho g >>= 16;
1905 1.1.8.2 jruoho b >>= 16;
1906 1.1.8.2 jruoho if ((unsigned) r > 255) { if (r < 0) r = 0; else r = 255; }
1907 1.1.8.2 jruoho if ((unsigned) g > 255) { if (g < 0) g = 0; else g = 255; }
1908 1.1.8.2 jruoho if ((unsigned) b > 255) { if (b < 0) b = 0; else b = 255; }
1909 1.1.8.2 jruoho out[0] = (uint8)r;
1910 1.1.8.2 jruoho out[1] = (uint8)g;
1911 1.1.8.2 jruoho out[2] = (uint8)b;
1912 1.1.8.2 jruoho out[3] = 255;
1913 1.1.8.2 jruoho out += step;
1914 1.1.8.2 jruoho }
1915 1.1.8.2 jruoho }
1916 1.1.8.2 jruoho
1917 1.1.8.2 jruoho #ifdef STBI_SIMD
1918 1.1.8.2 jruoho static stbi_YCbCr_to_RGB_run stbi_YCbCr_installed = YCbCr_to_RGB_row;
1919 1.1.8.2 jruoho
1920 1.1.8.2 jruoho void stbi_install_YCbCr_to_RGB(stbi_YCbCr_to_RGB_run func)
1921 1.1.8.2 jruoho {
1922 1.1.8.2 jruoho stbi_YCbCr_installed = func;
1923 1.1.8.2 jruoho }
1924 1.1.8.2 jruoho #endif
1925 1.1.8.2 jruoho
1926 1.1.8.2 jruoho
1927 1.1.8.2 jruoho // clean up the temporary component buffers
1928 1.1.8.2 jruoho static void cleanup_jpeg(jpeg *j)
1929 1.1.8.2 jruoho {
1930 1.1.8.2 jruoho int i;
1931 1.1.8.2 jruoho for (i=0; i < j->s.img_n; ++i) {
1932 1.1.8.2 jruoho if (j->img_comp[i].data) {
1933 1.1.8.2 jruoho FREE(j->img_comp[i].raw_data);
1934 1.1.8.2 jruoho j->img_comp[i].data = NULL;
1935 1.1.8.2 jruoho }
1936 1.1.8.2 jruoho if (j->img_comp[i].linebuf) {
1937 1.1.8.2 jruoho FREE(j->img_comp[i].linebuf);
1938 1.1.8.2 jruoho j->img_comp[i].linebuf = NULL;
1939 1.1.8.2 jruoho }
1940 1.1.8.2 jruoho }
1941 1.1.8.2 jruoho }
1942 1.1.8.2 jruoho
1943 1.1.8.2 jruoho typedef struct
1944 1.1.8.2 jruoho {
1945 1.1.8.2 jruoho resample_row_func resample;
1946 1.1.8.2 jruoho uint8 *line0,*line1;
1947 1.1.8.2 jruoho int hs,vs; // expansion factor in each axis
1948 1.1.8.2 jruoho int w_lores; // horizontal pixels pre-expansion
1949 1.1.8.2 jruoho int ystep; // how far through vertical expansion we are
1950 1.1.8.2 jruoho int ypos; // which pre-expansion row we're on
1951 1.1.8.2 jruoho } stbi_resample;
1952 1.1.8.2 jruoho
1953 1.1.8.2 jruoho static uint8 *load_jpeg_image(jpeg *z, int *out_x, int *out_y, int *comp, int req_comp)
1954 1.1.8.2 jruoho {
1955 1.1.8.2 jruoho int n, decode_n;
1956 1.1.8.2 jruoho // validate req_comp
1957 1.1.8.2 jruoho if (req_comp < 0 || req_comp > 4) return epuc("bad req_comp", "Internal error");
1958 1.1.8.2 jruoho z->s.img_n = 0;
1959 1.1.8.2 jruoho
1960 1.1.8.2 jruoho // load a jpeg image from whichever source
1961 1.1.8.2 jruoho if (!decode_jpeg_image(z)) { cleanup_jpeg(z); return NULL; }
1962 1.1.8.2 jruoho
1963 1.1.8.2 jruoho // determine actual number of components to generate
1964 1.1.8.2 jruoho n = req_comp ? req_comp : z->s.img_n;
1965 1.1.8.2 jruoho
1966 1.1.8.2 jruoho if (z->s.img_n == 3 && n < 3)
1967 1.1.8.2 jruoho decode_n = 1;
1968 1.1.8.2 jruoho else
1969 1.1.8.2 jruoho decode_n = z->s.img_n;
1970 1.1.8.2 jruoho
1971 1.1.8.2 jruoho // resample and color-convert
1972 1.1.8.2 jruoho {
1973 1.1.8.2 jruoho int k;
1974 1.1.8.2 jruoho uint i,j;
1975 1.1.8.2 jruoho uint8 *output;
1976 1.1.8.2 jruoho uint8 *coutput[4];
1977 1.1.8.2 jruoho
1978 1.1.8.2 jruoho stbi_resample res_comp[4];
1979 1.1.8.2 jruoho
1980 1.1.8.2 jruoho for (k=0; k < decode_n; ++k) {
1981 1.1.8.2 jruoho stbi_resample *r = &res_comp[k];
1982 1.1.8.2 jruoho
1983 1.1.8.2 jruoho // allocate line buffer big enough for upsampling off the edges
1984 1.1.8.2 jruoho // with upsample factor of 4
1985 1.1.8.2 jruoho z->img_comp[k].linebuf = (uint8 *) MALLOC(z->s.img_x + 3);
1986 1.1.8.2 jruoho if (!z->img_comp[k].linebuf) { cleanup_jpeg(z); return epuc("outofmem", "Out of memory"); }
1987 1.1.8.2 jruoho
1988 1.1.8.2 jruoho r->hs = z->img_h_max / z->img_comp[k].h;
1989 1.1.8.2 jruoho r->vs = z->img_v_max / z->img_comp[k].v;
1990 1.1.8.2 jruoho r->ystep = r->vs >> 1;
1991 1.1.8.2 jruoho r->w_lores = (z->s.img_x + r->hs-1) / r->hs;
1992 1.1.8.2 jruoho r->ypos = 0;
1993 1.1.8.2 jruoho r->line0 = r->line1 = z->img_comp[k].data;
1994 1.1.8.2 jruoho
1995 1.1.8.2 jruoho if (r->hs == 1 && r->vs == 1) r->resample = resample_row_1;
1996 1.1.8.2 jruoho else if (r->hs == 1 && r->vs == 2) r->resample = resample_row_v_2;
1997 1.1.8.2 jruoho else if (r->hs == 2 && r->vs == 1) r->resample = resample_row_h_2;
1998 1.1.8.2 jruoho else if (r->hs == 2 && r->vs == 2) r->resample = resample_row_hv_2;
1999 1.1.8.2 jruoho else r->resample = resample_row_generic;
2000 1.1.8.2 jruoho }
2001 1.1.8.2 jruoho
2002 1.1.8.2 jruoho // can't error after this so, this is safe
2003 1.1.8.2 jruoho output = (uint8 *) MALLOC(n * z->s.img_x * z->s.img_y + 1);
2004 1.1.8.2 jruoho if (!output) { cleanup_jpeg(z); return epuc("outofmem", "Out of memory"); }
2005 1.1.8.2 jruoho
2006 1.1.8.2 jruoho // now go ahead and resample
2007 1.1.8.2 jruoho for (j=0; j < z->s.img_y; ++j) {
2008 1.1.8.2 jruoho uint8 *out = output + n * z->s.img_x * j;
2009 1.1.8.2 jruoho for (k=0; k < decode_n; ++k) {
2010 1.1.8.2 jruoho stbi_resample *r = &res_comp[k];
2011 1.1.8.2 jruoho int y_bot = r->ystep >= (r->vs >> 1);
2012 1.1.8.2 jruoho coutput[k] = r->resample(z->img_comp[k].linebuf,
2013 1.1.8.2 jruoho y_bot ? r->line1 : r->line0,
2014 1.1.8.2 jruoho y_bot ? r->line0 : r->line1,
2015 1.1.8.2 jruoho r->w_lores, r->hs);
2016 1.1.8.2 jruoho if (++r->ystep >= r->vs) {
2017 1.1.8.2 jruoho r->ystep = 0;
2018 1.1.8.2 jruoho r->line0 = r->line1;
2019 1.1.8.2 jruoho if (++r->ypos < z->img_comp[k].y)
2020 1.1.8.2 jruoho r->line1 += z->img_comp[k].w2;
2021 1.1.8.2 jruoho }
2022 1.1.8.2 jruoho }
2023 1.1.8.2 jruoho if (n >= 3) {
2024 1.1.8.2 jruoho uint8 *y = coutput[0];
2025 1.1.8.2 jruoho if (z->s.img_n == 3) {
2026 1.1.8.2 jruoho #ifdef STBI_SIMD
2027 1.1.8.2 jruoho stbi_YCbCr_installed(out, y, coutput[1], coutput[2], z->s.img_x, n);
2028 1.1.8.2 jruoho #else
2029 1.1.8.2 jruoho YCbCr_to_RGB_row(out, y, coutput[1], coutput[2], z->s.img_x, n);
2030 1.1.8.2 jruoho #endif
2031 1.1.8.2 jruoho } else
2032 1.1.8.2 jruoho for (i=0; i < z->s.img_x; ++i) {
2033 1.1.8.2 jruoho out[0] = out[1] = out[2] = y[i];
2034 1.1.8.2 jruoho out[3] = 255; // not used if n==3
2035 1.1.8.2 jruoho out += n;
2036 1.1.8.2 jruoho }
2037 1.1.8.2 jruoho } else {
2038 1.1.8.2 jruoho uint8 *y = coutput[0];
2039 1.1.8.2 jruoho if (n == 1)
2040 1.1.8.2 jruoho for (i=0; i < z->s.img_x; ++i) out[i] = y[i];
2041 1.1.8.2 jruoho else
2042 1.1.8.2 jruoho for (i=0; i < z->s.img_x; ++i) *out++ = y[i], *out++ = 255;
2043 1.1.8.2 jruoho }
2044 1.1.8.2 jruoho }
2045 1.1.8.2 jruoho cleanup_jpeg(z);
2046 1.1.8.2 jruoho *out_x = z->s.img_x;
2047 1.1.8.2 jruoho *out_y = z->s.img_y;
2048 1.1.8.2 jruoho if (comp) *comp = z->s.img_n; // report original components, not output
2049 1.1.8.2 jruoho return output;
2050 1.1.8.2 jruoho }
2051 1.1.8.2 jruoho }
2052 1.1.8.2 jruoho
2053 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
2054 1.1.8.2 jruoho unsigned char *stbi_jpeg_load_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
2055 1.1.8.2 jruoho {
2056 1.1.8.2 jruoho jpeg j;
2057 1.1.8.2 jruoho start_file(&j.s, f);
2058 1.1.8.2 jruoho return load_jpeg_image(&j, x,y,comp,req_comp);
2059 1.1.8.2 jruoho }
2060 1.1.8.2 jruoho
2061 1.1.8.2 jruoho unsigned char *stbi_jpeg_load(char const *filename, int *x, int *y, int *comp, int req_comp)
2062 1.1.8.2 jruoho {
2063 1.1.8.2 jruoho unsigned char *data;
2064 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
2065 1.1.8.2 jruoho if (!f) return NULL;
2066 1.1.8.2 jruoho data = stbi_jpeg_load_from_file(f,x,y,comp,req_comp);
2067 1.1.8.2 jruoho fclose(f);
2068 1.1.8.2 jruoho return data;
2069 1.1.8.2 jruoho }
2070 1.1.8.2 jruoho #endif
2071 1.1.8.2 jruoho
2072 1.1.8.2 jruoho unsigned char *stbi_jpeg_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
2073 1.1.8.2 jruoho {
2074 1.1.8.2 jruoho #ifdef STBI_SMALL_STACK
2075 1.1.8.2 jruoho unsigned char *result;
2076 1.1.8.2 jruoho jpeg *j = (jpeg *) MALLOC(sizeof(*j));
2077 1.1.8.2 jruoho start_mem(&j->s, buffer, len);
2078 1.1.8.2 jruoho result = load_jpeg_image(j,x,y,comp,req_comp);
2079 1.1.8.2 jruoho FREE(j);
2080 1.1.8.2 jruoho return result;
2081 1.1.8.2 jruoho #else
2082 1.1.8.2 jruoho jpeg j;
2083 1.1.8.2 jruoho start_mem(&j.s, buffer,len);
2084 1.1.8.2 jruoho return load_jpeg_image(&j, x,y,comp,req_comp);
2085 1.1.8.2 jruoho #endif
2086 1.1.8.2 jruoho }
2087 1.1.8.2 jruoho
2088 1.1.8.2 jruoho static int stbi_jpeg_info_raw(jpeg *j, int *x, int *y, int *comp)
2089 1.1.8.2 jruoho {
2090 1.1.8.2 jruoho if (!decode_jpeg_header(j, SCAN_header))
2091 1.1.8.2 jruoho return 0;
2092 1.1.8.2 jruoho if (x) *x = j->s.img_x;
2093 1.1.8.2 jruoho if (y) *y = j->s.img_y;
2094 1.1.8.2 jruoho if (comp) *comp = j->s.img_n;
2095 1.1.8.2 jruoho return 1;
2096 1.1.8.2 jruoho }
2097 1.1.8.2 jruoho
2098 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
2099 1.1.8.2 jruoho int stbi_jpeg_test_file(FILE *f)
2100 1.1.8.2 jruoho {
2101 1.1.8.2 jruoho int n,r;
2102 1.1.8.2 jruoho jpeg j;
2103 1.1.8.2 jruoho n = ftell(f);
2104 1.1.8.2 jruoho start_file(&j.s, f);
2105 1.1.8.2 jruoho r = decode_jpeg_header(&j, SCAN_type);
2106 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
2107 1.1.8.2 jruoho return r;
2108 1.1.8.2 jruoho }
2109 1.1.8.2 jruoho
2110 1.1.8.2 jruoho int stbi_jpeg_info_from_file(FILE *f, int *x, int *y, int *comp)
2111 1.1.8.2 jruoho {
2112 1.1.8.2 jruoho jpeg j;
2113 1.1.8.2 jruoho long n = ftell(f);
2114 1.1.8.2 jruoho int res;
2115 1.1.8.2 jruoho start_file(&j.s, f);
2116 1.1.8.2 jruoho res = stbi_jpeg_info_raw(&j, x, y, comp);
2117 1.1.8.2 jruoho fseek(f, n, SEEK_SET);
2118 1.1.8.2 jruoho return res;
2119 1.1.8.2 jruoho }
2120 1.1.8.2 jruoho
2121 1.1.8.2 jruoho int stbi_jpeg_info(char const *filename, int *x, int *y, int *comp)
2122 1.1.8.2 jruoho {
2123 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
2124 1.1.8.2 jruoho int result;
2125 1.1.8.2 jruoho if (!f) return e("can't fopen", "Unable to open file");
2126 1.1.8.2 jruoho result = stbi_jpeg_info_from_file(f, x, y, comp);
2127 1.1.8.2 jruoho fclose(f);
2128 1.1.8.2 jruoho return result;
2129 1.1.8.2 jruoho }
2130 1.1.8.2 jruoho #endif
2131 1.1.8.2 jruoho
2132 1.1.8.2 jruoho int stbi_jpeg_test_memory(stbi_uc const *buffer, int len)
2133 1.1.8.2 jruoho {
2134 1.1.8.2 jruoho jpeg j;
2135 1.1.8.2 jruoho start_mem(&j.s, buffer,len);
2136 1.1.8.2 jruoho return decode_jpeg_header(&j, SCAN_type);
2137 1.1.8.2 jruoho }
2138 1.1.8.2 jruoho
2139 1.1.8.2 jruoho int stbi_jpeg_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp)
2140 1.1.8.2 jruoho {
2141 1.1.8.2 jruoho jpeg j;
2142 1.1.8.2 jruoho start_mem(&j.s, buffer, len);
2143 1.1.8.2 jruoho return stbi_jpeg_info_raw(&j, x, y, comp);
2144 1.1.8.2 jruoho }
2145 1.1.8.2 jruoho
2146 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
2147 1.1.8.2 jruoho extern int stbi_jpeg_info (char const *filename, int *x, int *y, int *comp);
2148 1.1.8.2 jruoho extern int stbi_jpeg_info_from_file (FILE *f, int *x, int *y, int *comp);
2149 1.1.8.2 jruoho #endif
2150 1.1.8.2 jruoho extern int stbi_jpeg_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp);
2151 1.1.8.2 jruoho
2152 1.1.8.2 jruoho // public domain zlib decode v0.2 Sean Barrett 2006-11-18
2153 1.1.8.2 jruoho // simple implementation
2154 1.1.8.2 jruoho // - all input must be provided in an upfront buffer
2155 1.1.8.2 jruoho // - all output is written to a single output buffer (can malloc/realloc)
2156 1.1.8.2 jruoho // performance
2157 1.1.8.2 jruoho // - fast huffman
2158 1.1.8.2 jruoho
2159 1.1.8.2 jruoho // fast-way is faster to check than jpeg huffman, but slow way is slower
2160 1.1.8.2 jruoho #define ZFAST_BITS 9 // accelerate all cases in default tables
2161 1.1.8.2 jruoho #define ZFAST_MASK ((1 << ZFAST_BITS) - 1)
2162 1.1.8.2 jruoho
2163 1.1.8.2 jruoho // zlib-style huffman encoding
2164 1.1.8.2 jruoho // (jpegs packs from left, zlib from right, so can't share code)
2165 1.1.8.2 jruoho typedef struct
2166 1.1.8.2 jruoho {
2167 1.1.8.2 jruoho uint16 fast[1 << ZFAST_BITS];
2168 1.1.8.2 jruoho uint16 firstcode[16];
2169 1.1.8.2 jruoho int maxcode[17];
2170 1.1.8.2 jruoho uint16 firstsymbol[16];
2171 1.1.8.2 jruoho uint8 size[288];
2172 1.1.8.2 jruoho uint16 value[288];
2173 1.1.8.2 jruoho } zhuffman;
2174 1.1.8.2 jruoho
2175 1.1.8.2 jruoho __forceinline static int bitreverse16(int n)
2176 1.1.8.2 jruoho {
2177 1.1.8.2 jruoho n = ((n & 0xAAAA) >> 1) | ((n & 0x5555) << 1);
2178 1.1.8.2 jruoho n = ((n & 0xCCCC) >> 2) | ((n & 0x3333) << 2);
2179 1.1.8.2 jruoho n = ((n & 0xF0F0) >> 4) | ((n & 0x0F0F) << 4);
2180 1.1.8.2 jruoho n = ((n & 0xFF00) >> 8) | ((n & 0x00FF) << 8);
2181 1.1.8.2 jruoho return n;
2182 1.1.8.2 jruoho }
2183 1.1.8.2 jruoho
2184 1.1.8.2 jruoho __forceinline static int bit_reverse(int v, int bits)
2185 1.1.8.2 jruoho {
2186 1.1.8.2 jruoho assert(bits <= 16);
2187 1.1.8.2 jruoho // to bit reverse n bits, reverse 16 and shift
2188 1.1.8.2 jruoho // e.g. 11 bits, bit reverse and shift away 5
2189 1.1.8.2 jruoho return bitreverse16(v) >> (16-bits);
2190 1.1.8.2 jruoho }
2191 1.1.8.2 jruoho
2192 1.1.8.2 jruoho static int zbuild_huffman(zhuffman *z, uint8 *sizelist, int num)
2193 1.1.8.2 jruoho {
2194 1.1.8.2 jruoho int i,k=0;
2195 1.1.8.2 jruoho int code, next_code[16], sizes[17];
2196 1.1.8.2 jruoho
2197 1.1.8.2 jruoho // DEFLATE spec for generating codes
2198 1.1.8.2 jruoho memset(sizes, 0, sizeof(sizes));
2199 1.1.8.2 jruoho memset(z->fast, 255, sizeof(z->fast));
2200 1.1.8.2 jruoho for (i=0; i < num; ++i)
2201 1.1.8.2 jruoho ++sizes[sizelist[i]];
2202 1.1.8.2 jruoho sizes[0] = 0;
2203 1.1.8.2 jruoho for (i=1; i < 16; ++i)
2204 1.1.8.2 jruoho assert(sizes[i] <= (1 << i));
2205 1.1.8.2 jruoho code = 0;
2206 1.1.8.2 jruoho for (i=1; i < 16; ++i) {
2207 1.1.8.2 jruoho next_code[i] = code;
2208 1.1.8.2 jruoho z->firstcode[i] = (uint16) code;
2209 1.1.8.2 jruoho z->firstsymbol[i] = (uint16) k;
2210 1.1.8.2 jruoho code = (code + sizes[i]);
2211 1.1.8.2 jruoho if (sizes[i])
2212 1.1.8.2 jruoho if (code-1 >= (1 << i)) return e("bad codelengths","Corrupt JPEG");
2213 1.1.8.2 jruoho z->maxcode[i] = code << (16-i); // preshift for inner loop
2214 1.1.8.2 jruoho code <<= 1;
2215 1.1.8.2 jruoho k += sizes[i];
2216 1.1.8.2 jruoho }
2217 1.1.8.2 jruoho z->maxcode[16] = 0x10000; // sentinel
2218 1.1.8.2 jruoho for (i=0; i < num; ++i) {
2219 1.1.8.2 jruoho int s = sizelist[i];
2220 1.1.8.2 jruoho if (s) {
2221 1.1.8.2 jruoho int c = next_code[s] - z->firstcode[s] + z->firstsymbol[s];
2222 1.1.8.2 jruoho z->size[c] = (uint8)s;
2223 1.1.8.2 jruoho z->value[c] = (uint16)i;
2224 1.1.8.2 jruoho if (s <= ZFAST_BITS) {
2225 1.1.8.2 jruoho int m = bit_reverse(next_code[s],s);
2226 1.1.8.2 jruoho while (m < (1 << ZFAST_BITS)) {
2227 1.1.8.2 jruoho z->fast[m] = (uint16) c;
2228 1.1.8.2 jruoho m += (1 << s);
2229 1.1.8.2 jruoho }
2230 1.1.8.2 jruoho }
2231 1.1.8.2 jruoho ++next_code[s];
2232 1.1.8.2 jruoho }
2233 1.1.8.2 jruoho }
2234 1.1.8.2 jruoho return 1;
2235 1.1.8.2 jruoho }
2236 1.1.8.2 jruoho
2237 1.1.8.2 jruoho // zlib-from-memory implementation for PNG reading
2238 1.1.8.2 jruoho // because PNG allows splitting the zlib stream arbitrarily,
2239 1.1.8.2 jruoho // and it's annoying structurally to have PNG call ZLIB call PNG,
2240 1.1.8.2 jruoho // we require PNG read all the IDATs and combine them into a single
2241 1.1.8.2 jruoho // memory buffer
2242 1.1.8.2 jruoho
2243 1.1.8.2 jruoho typedef struct
2244 1.1.8.2 jruoho {
2245 1.1.8.2 jruoho uint8 const *zbuffer, *zbuffer_end;
2246 1.1.8.2 jruoho int num_bits;
2247 1.1.8.2 jruoho uint32 code_buffer;
2248 1.1.8.2 jruoho
2249 1.1.8.2 jruoho char *zout;
2250 1.1.8.2 jruoho char *zout_start;
2251 1.1.8.2 jruoho char *zout_end;
2252 1.1.8.2 jruoho int z_expandable;
2253 1.1.8.2 jruoho
2254 1.1.8.2 jruoho zhuffman z_length, z_distance;
2255 1.1.8.2 jruoho } zbuf;
2256 1.1.8.2 jruoho
2257 1.1.8.2 jruoho __forceinline static int zget8(zbuf *z)
2258 1.1.8.2 jruoho {
2259 1.1.8.2 jruoho if (z->zbuffer >= z->zbuffer_end) return 0;
2260 1.1.8.2 jruoho return *z->zbuffer++;
2261 1.1.8.2 jruoho }
2262 1.1.8.2 jruoho
2263 1.1.8.2 jruoho static void fill_bits(zbuf *z)
2264 1.1.8.2 jruoho {
2265 1.1.8.2 jruoho do {
2266 1.1.8.2 jruoho assert(z->code_buffer < (1U << z->num_bits));
2267 1.1.8.2 jruoho z->code_buffer |= zget8(z) << z->num_bits;
2268 1.1.8.2 jruoho z->num_bits += 8;
2269 1.1.8.2 jruoho } while (z->num_bits <= 24);
2270 1.1.8.2 jruoho }
2271 1.1.8.2 jruoho
2272 1.1.8.2 jruoho __forceinline static unsigned int zreceive(zbuf *z, int n)
2273 1.1.8.2 jruoho {
2274 1.1.8.2 jruoho unsigned int k;
2275 1.1.8.2 jruoho if (z->num_bits < n) fill_bits(z);
2276 1.1.8.2 jruoho k = z->code_buffer & ((1 << n) - 1);
2277 1.1.8.2 jruoho z->code_buffer >>= n;
2278 1.1.8.2 jruoho z->num_bits -= n;
2279 1.1.8.2 jruoho return k;
2280 1.1.8.2 jruoho }
2281 1.1.8.2 jruoho
2282 1.1.8.2 jruoho __forceinline static int zhuffman_decode(zbuf *a, zhuffman *z)
2283 1.1.8.2 jruoho {
2284 1.1.8.2 jruoho int b,s,k;
2285 1.1.8.2 jruoho if (a->num_bits < 16) fill_bits(a);
2286 1.1.8.2 jruoho b = z->fast[a->code_buffer & ZFAST_MASK];
2287 1.1.8.2 jruoho if (b < 0xffff) {
2288 1.1.8.2 jruoho s = z->size[b];
2289 1.1.8.2 jruoho a->code_buffer >>= s;
2290 1.1.8.2 jruoho a->num_bits -= s;
2291 1.1.8.2 jruoho return z->value[b];
2292 1.1.8.2 jruoho }
2293 1.1.8.2 jruoho
2294 1.1.8.2 jruoho // not resolved by fast table, so compute it the slow way
2295 1.1.8.2 jruoho // use jpeg approach, which requires MSbits at top
2296 1.1.8.2 jruoho k = bit_reverse(a->code_buffer, 16);
2297 1.1.8.2 jruoho for (s=ZFAST_BITS+1; ; ++s)
2298 1.1.8.2 jruoho if (k < z->maxcode[s])
2299 1.1.8.2 jruoho break;
2300 1.1.8.2 jruoho if (s == 16) return -1; // invalid code!
2301 1.1.8.2 jruoho // code size is s, so:
2302 1.1.8.2 jruoho b = (k >> (16-s)) - z->firstcode[s] + z->firstsymbol[s];
2303 1.1.8.2 jruoho assert(z->size[b] == s);
2304 1.1.8.2 jruoho a->code_buffer >>= s;
2305 1.1.8.2 jruoho a->num_bits -= s;
2306 1.1.8.2 jruoho return z->value[b];
2307 1.1.8.2 jruoho }
2308 1.1.8.2 jruoho
2309 1.1.8.2 jruoho static int expand(zbuf *z, int n) // need to make room for n bytes
2310 1.1.8.2 jruoho {
2311 1.1.8.2 jruoho char *q;
2312 1.1.8.2 jruoho int cur, limit;
2313 1.1.8.2 jruoho if (!z->z_expandable) return e("output buffer limit","Corrupt PNG");
2314 1.1.8.2 jruoho cur = (int) (z->zout - z->zout_start);
2315 1.1.8.2 jruoho limit = (int) (z->zout_end - z->zout_start);
2316 1.1.8.2 jruoho while (cur + n > limit)
2317 1.1.8.2 jruoho limit *= 2;
2318 1.1.8.2 jruoho q = (char *) REALLOC(z->zout_start, limit);
2319 1.1.8.2 jruoho if (q == NULL) return e("outofmem", "Out of memory");
2320 1.1.8.2 jruoho z->zout_start = q;
2321 1.1.8.2 jruoho z->zout = q + cur;
2322 1.1.8.2 jruoho z->zout_end = q + limit;
2323 1.1.8.2 jruoho return 1;
2324 1.1.8.2 jruoho }
2325 1.1.8.2 jruoho
2326 1.1.8.2 jruoho static int length_base[31] = {
2327 1.1.8.2 jruoho 3,4,5,6,7,8,9,10,11,13,
2328 1.1.8.2 jruoho 15,17,19,23,27,31,35,43,51,59,
2329 1.1.8.2 jruoho 67,83,99,115,131,163,195,227,258,0,0 };
2330 1.1.8.2 jruoho
2331 1.1.8.2 jruoho static int length_extra[31]=
2332 1.1.8.2 jruoho { 0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0,0,0 };
2333 1.1.8.2 jruoho
2334 1.1.8.2 jruoho static int dist_base[32] = { 1,2,3,4,5,7,9,13,17,25,33,49,65,97,129,193,
2335 1.1.8.2 jruoho 257,385,513,769,1025,1537,2049,3073,4097,6145,8193,12289,16385,24577,0,0};
2336 1.1.8.2 jruoho
2337 1.1.8.2 jruoho static int dist_extra[32] =
2338 1.1.8.2 jruoho { 0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13};
2339 1.1.8.2 jruoho
2340 1.1.8.2 jruoho static int parse_huffman_block(zbuf *a)
2341 1.1.8.2 jruoho {
2342 1.1.8.2 jruoho for(;;) {
2343 1.1.8.2 jruoho int z = zhuffman_decode(a, &a->z_length);
2344 1.1.8.2 jruoho if (z < 256) {
2345 1.1.8.2 jruoho if (z < 0) return e("bad huffman code","Corrupt PNG"); // error in huffman codes
2346 1.1.8.2 jruoho if (a->zout >= a->zout_end) if (!expand(a, 1)) return 0;
2347 1.1.8.2 jruoho *a->zout++ = (char) z;
2348 1.1.8.2 jruoho } else {
2349 1.1.8.2 jruoho uint8 *p;
2350 1.1.8.2 jruoho int len,dist;
2351 1.1.8.2 jruoho if (z == 256) return 1;
2352 1.1.8.2 jruoho z -= 257;
2353 1.1.8.2 jruoho len = length_base[z];
2354 1.1.8.2 jruoho if (length_extra[z]) len += zreceive(a, length_extra[z]);
2355 1.1.8.2 jruoho z = zhuffman_decode(a, &a->z_distance);
2356 1.1.8.2 jruoho if (z < 0) return e("bad huffman code","Corrupt PNG");
2357 1.1.8.2 jruoho dist = dist_base[z];
2358 1.1.8.2 jruoho if (dist_extra[z]) dist += zreceive(a, dist_extra[z]);
2359 1.1.8.2 jruoho if (a->zout - a->zout_start < dist) return e("bad dist","Corrupt PNG");
2360 1.1.8.2 jruoho if (a->zout + len > a->zout_end) if (!expand(a, len)) return 0;
2361 1.1.8.2 jruoho p = (uint8 *) (a->zout - dist);
2362 1.1.8.2 jruoho while (len--)
2363 1.1.8.2 jruoho *a->zout++ = *p++;
2364 1.1.8.2 jruoho }
2365 1.1.8.2 jruoho }
2366 1.1.8.2 jruoho }
2367 1.1.8.2 jruoho
2368 1.1.8.2 jruoho static int compute_huffman_codes(zbuf *a)
2369 1.1.8.2 jruoho {
2370 1.1.8.2 jruoho static uint8 length_dezigzag[19] = { 16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15 };
2371 1.1.8.2 jruoho zhuffman z_codelength;
2372 1.1.8.2 jruoho uint8 lencodes[286+32+137];//padding for maximum single op
2373 1.1.8.2 jruoho uint8 codelength_sizes[19];
2374 1.1.8.2 jruoho int i,n;
2375 1.1.8.2 jruoho
2376 1.1.8.2 jruoho int hlit = zreceive(a,5) + 257;
2377 1.1.8.2 jruoho int hdist = zreceive(a,5) + 1;
2378 1.1.8.2 jruoho int hclen = zreceive(a,4) + 4;
2379 1.1.8.2 jruoho
2380 1.1.8.2 jruoho memset(codelength_sizes, 0, sizeof(codelength_sizes));
2381 1.1.8.2 jruoho for (i=0; i < hclen; ++i) {
2382 1.1.8.2 jruoho int s = zreceive(a,3);
2383 1.1.8.2 jruoho codelength_sizes[length_dezigzag[i]] = (uint8) s;
2384 1.1.8.2 jruoho }
2385 1.1.8.2 jruoho if (!zbuild_huffman(&z_codelength, codelength_sizes, 19)) return 0;
2386 1.1.8.2 jruoho
2387 1.1.8.2 jruoho n = 0;
2388 1.1.8.2 jruoho while (n < hlit + hdist) {
2389 1.1.8.2 jruoho int c = zhuffman_decode(a, &z_codelength);
2390 1.1.8.2 jruoho assert(c >= 0 && c < 19);
2391 1.1.8.2 jruoho if (c < 16)
2392 1.1.8.2 jruoho lencodes[n++] = (uint8) c;
2393 1.1.8.2 jruoho else if (c == 16) {
2394 1.1.8.2 jruoho c = zreceive(a,2)+3;
2395 1.1.8.2 jruoho memset(lencodes+n, lencodes[n-1], c);
2396 1.1.8.2 jruoho n += c;
2397 1.1.8.2 jruoho } else if (c == 17) {
2398 1.1.8.2 jruoho c = zreceive(a,3)+3;
2399 1.1.8.2 jruoho memset(lencodes+n, 0, c);
2400 1.1.8.2 jruoho n += c;
2401 1.1.8.2 jruoho } else {
2402 1.1.8.2 jruoho assert(c == 18);
2403 1.1.8.2 jruoho c = zreceive(a,7)+11;
2404 1.1.8.2 jruoho memset(lencodes+n, 0, c);
2405 1.1.8.2 jruoho n += c;
2406 1.1.8.2 jruoho }
2407 1.1.8.2 jruoho }
2408 1.1.8.2 jruoho if (n != hlit+hdist) return e("bad codelengths","Corrupt PNG");
2409 1.1.8.2 jruoho if (!zbuild_huffman(&a->z_length, lencodes, hlit)) return 0;
2410 1.1.8.2 jruoho if (!zbuild_huffman(&a->z_distance, lencodes+hlit, hdist)) return 0;
2411 1.1.8.2 jruoho return 1;
2412 1.1.8.2 jruoho }
2413 1.1.8.2 jruoho
2414 1.1.8.2 jruoho static int parse_uncompressed_block(zbuf *a)
2415 1.1.8.2 jruoho {
2416 1.1.8.2 jruoho uint8 header[4];
2417 1.1.8.2 jruoho int len,nlen,k;
2418 1.1.8.2 jruoho if (a->num_bits & 7)
2419 1.1.8.2 jruoho zreceive(a, a->num_bits & 7); // discard
2420 1.1.8.2 jruoho // drain the bit-packed data into header
2421 1.1.8.2 jruoho k = 0;
2422 1.1.8.2 jruoho while (a->num_bits > 0) {
2423 1.1.8.2 jruoho header[k++] = (uint8) (a->code_buffer & 255); // wtf this warns?
2424 1.1.8.2 jruoho a->code_buffer >>= 8;
2425 1.1.8.2 jruoho a->num_bits -= 8;
2426 1.1.8.2 jruoho }
2427 1.1.8.2 jruoho assert(a->num_bits == 0);
2428 1.1.8.2 jruoho // now fill header the normal way
2429 1.1.8.2 jruoho while (k < 4)
2430 1.1.8.2 jruoho header[k++] = (uint8) zget8(a);
2431 1.1.8.2 jruoho len = header[1] * 256 + header[0];
2432 1.1.8.2 jruoho nlen = header[3] * 256 + header[2];
2433 1.1.8.2 jruoho if (nlen != (len ^ 0xffff)) return e("zlib corrupt","Corrupt PNG");
2434 1.1.8.2 jruoho if (a->zbuffer + len > a->zbuffer_end) return e("read past buffer","Corrupt PNG");
2435 1.1.8.2 jruoho if (a->zout + len > a->zout_end)
2436 1.1.8.2 jruoho if (!expand(a, len)) return 0;
2437 1.1.8.2 jruoho memcpy(a->zout, a->zbuffer, len);
2438 1.1.8.2 jruoho a->zbuffer += len;
2439 1.1.8.2 jruoho a->zout += len;
2440 1.1.8.2 jruoho return 1;
2441 1.1.8.2 jruoho }
2442 1.1.8.2 jruoho
2443 1.1.8.2 jruoho static int parse_zlib_header(zbuf *a)
2444 1.1.8.2 jruoho {
2445 1.1.8.2 jruoho int cmf = zget8(a);
2446 1.1.8.2 jruoho int cm = cmf & 15;
2447 1.1.8.2 jruoho /* int cinfo = cmf >> 4; */
2448 1.1.8.2 jruoho int flg = zget8(a);
2449 1.1.8.2 jruoho if ((cmf*256+flg) % 31 != 0) return e("bad zlib header","Corrupt PNG"); // zlib spec
2450 1.1.8.2 jruoho if (flg & 32) return e("no preset dict","Corrupt PNG"); // preset dictionary not allowed in png
2451 1.1.8.2 jruoho if (cm != 8) return e("bad compression","Corrupt PNG"); // DEFLATE required for png
2452 1.1.8.2 jruoho // window = 1 << (8 + cinfo)... but who cares, we fully buffer output
2453 1.1.8.2 jruoho return 1;
2454 1.1.8.2 jruoho }
2455 1.1.8.2 jruoho
2456 1.1.8.2 jruoho // @TODO: should statically initialize these for optimal thread safety
2457 1.1.8.2 jruoho static uint8 default_length[288], default_distance[32];
2458 1.1.8.2 jruoho static void init_defaults(void)
2459 1.1.8.2 jruoho {
2460 1.1.8.2 jruoho int i; // use <= to match clearly with spec
2461 1.1.8.2 jruoho for (i=0; i <= 143; ++i) default_length[i] = 8;
2462 1.1.8.2 jruoho for ( ; i <= 255; ++i) default_length[i] = 9;
2463 1.1.8.2 jruoho for ( ; i <= 279; ++i) default_length[i] = 7;
2464 1.1.8.2 jruoho for ( ; i <= 287; ++i) default_length[i] = 8;
2465 1.1.8.2 jruoho
2466 1.1.8.2 jruoho for (i=0; i <= 31; ++i) default_distance[i] = 5;
2467 1.1.8.2 jruoho }
2468 1.1.8.2 jruoho
2469 1.1.8.2 jruoho int stbi_png_partial; // a quick hack to only allow decoding some of a PNG... I should implement real streaming support instead
2470 1.1.8.2 jruoho static int parse_zlib(zbuf *a, int parse_header)
2471 1.1.8.2 jruoho {
2472 1.1.8.2 jruoho int final, type;
2473 1.1.8.2 jruoho if (parse_header)
2474 1.1.8.2 jruoho if (!parse_zlib_header(a)) return 0;
2475 1.1.8.2 jruoho a->num_bits = 0;
2476 1.1.8.2 jruoho a->code_buffer = 0;
2477 1.1.8.2 jruoho do {
2478 1.1.8.2 jruoho final = zreceive(a,1);
2479 1.1.8.2 jruoho type = zreceive(a,2);
2480 1.1.8.2 jruoho if (type == 0) {
2481 1.1.8.2 jruoho if (!parse_uncompressed_block(a)) return 0;
2482 1.1.8.2 jruoho } else if (type == 3) {
2483 1.1.8.2 jruoho return 0;
2484 1.1.8.2 jruoho } else {
2485 1.1.8.2 jruoho if (type == 1) {
2486 1.1.8.2 jruoho // use fixed code lengths
2487 1.1.8.2 jruoho if (!default_distance[31]) init_defaults();
2488 1.1.8.2 jruoho if (!zbuild_huffman(&a->z_length , default_length , 288)) return 0;
2489 1.1.8.2 jruoho if (!zbuild_huffman(&a->z_distance, default_distance, 32)) return 0;
2490 1.1.8.2 jruoho } else {
2491 1.1.8.2 jruoho if (!compute_huffman_codes(a)) return 0;
2492 1.1.8.2 jruoho }
2493 1.1.8.2 jruoho if (!parse_huffman_block(a)) return 0;
2494 1.1.8.2 jruoho }
2495 1.1.8.2 jruoho if (stbi_png_partial && a->zout - a->zout_start > 65536)
2496 1.1.8.2 jruoho break;
2497 1.1.8.2 jruoho } while (!final);
2498 1.1.8.2 jruoho return 1;
2499 1.1.8.2 jruoho }
2500 1.1.8.2 jruoho
2501 1.1.8.2 jruoho static int do_zlib(zbuf *a, char *obuf, int olen, int exp, int parse_header)
2502 1.1.8.2 jruoho {
2503 1.1.8.2 jruoho a->zout_start = obuf;
2504 1.1.8.2 jruoho a->zout = obuf;
2505 1.1.8.2 jruoho a->zout_end = obuf + olen;
2506 1.1.8.2 jruoho a->z_expandable = exp;
2507 1.1.8.2 jruoho
2508 1.1.8.2 jruoho return parse_zlib(a, parse_header);
2509 1.1.8.2 jruoho }
2510 1.1.8.2 jruoho
2511 1.1.8.2 jruoho char *stbi_zlib_decode_malloc_guesssize(const char * buffer, int len, int initial_size, int *outlen)
2512 1.1.8.2 jruoho {
2513 1.1.8.2 jruoho zbuf a;
2514 1.1.8.2 jruoho char *p = (char *) MALLOC(initial_size);
2515 1.1.8.2 jruoho if (p == NULL) return NULL;
2516 1.1.8.2 jruoho a.zbuffer = (uint8 const *) buffer;
2517 1.1.8.2 jruoho a.zbuffer_end = (uint8 const *) buffer + len;
2518 1.1.8.2 jruoho if (do_zlib(&a, p, initial_size, 1, 1)) {
2519 1.1.8.2 jruoho if (outlen) *outlen = (int) (a.zout - a.zout_start);
2520 1.1.8.2 jruoho return a.zout_start;
2521 1.1.8.2 jruoho } else {
2522 1.1.8.2 jruoho FREE(a.zout_start);
2523 1.1.8.2 jruoho return NULL;
2524 1.1.8.2 jruoho }
2525 1.1.8.2 jruoho }
2526 1.1.8.2 jruoho
2527 1.1.8.2 jruoho char *stbi_zlib_decode_malloc(char const *buffer, int len, int *outlen)
2528 1.1.8.2 jruoho {
2529 1.1.8.2 jruoho return stbi_zlib_decode_malloc_guesssize(buffer, len, 16384, outlen);
2530 1.1.8.2 jruoho }
2531 1.1.8.2 jruoho
2532 1.1.8.2 jruoho char *stbi_zlib_decode_malloc_guesssize_headerflag(const char *buffer, int len, int initial_size, int *outlen, int parse_header)
2533 1.1.8.2 jruoho {
2534 1.1.8.2 jruoho zbuf a;
2535 1.1.8.2 jruoho char *p = (char *) MALLOC(initial_size);
2536 1.1.8.2 jruoho if (p == NULL) return NULL;
2537 1.1.8.2 jruoho a.zbuffer = (uint8 const *) buffer;
2538 1.1.8.2 jruoho a.zbuffer_end = (uint8 const *) buffer + len;
2539 1.1.8.2 jruoho if (do_zlib(&a, p, initial_size, 1, parse_header)) {
2540 1.1.8.2 jruoho if (outlen) *outlen = (int) (a.zout - a.zout_start);
2541 1.1.8.2 jruoho return a.zout_start;
2542 1.1.8.2 jruoho } else {
2543 1.1.8.2 jruoho FREE(a.zout_start);
2544 1.1.8.2 jruoho return NULL;
2545 1.1.8.2 jruoho }
2546 1.1.8.2 jruoho }
2547 1.1.8.2 jruoho
2548 1.1.8.2 jruoho int stbi_zlib_decode_buffer(char *obuffer, int olen, char const *ibuffer, int ilen)
2549 1.1.8.2 jruoho {
2550 1.1.8.2 jruoho zbuf a;
2551 1.1.8.2 jruoho a.zbuffer = (uint8 const *) ibuffer;
2552 1.1.8.2 jruoho a.zbuffer_end = (uint8 const *) ibuffer + ilen;
2553 1.1.8.2 jruoho if (do_zlib(&a, obuffer, olen, 0, 1))
2554 1.1.8.2 jruoho return (int) (a.zout - a.zout_start);
2555 1.1.8.2 jruoho else
2556 1.1.8.2 jruoho return -1;
2557 1.1.8.2 jruoho }
2558 1.1.8.2 jruoho
2559 1.1.8.2 jruoho char *stbi_zlib_decode_noheader_malloc(char const *buffer, int len, int *outlen)
2560 1.1.8.2 jruoho {
2561 1.1.8.2 jruoho zbuf a;
2562 1.1.8.2 jruoho char *p = (char *) MALLOC(16384);
2563 1.1.8.2 jruoho if (p == NULL) return NULL;
2564 1.1.8.2 jruoho a.zbuffer = (uint8 const *) buffer;
2565 1.1.8.2 jruoho a.zbuffer_end = (uint8 const *) buffer+len;
2566 1.1.8.2 jruoho if (do_zlib(&a, p, 16384, 1, 0)) {
2567 1.1.8.2 jruoho if (outlen) *outlen = (int) (a.zout - a.zout_start);
2568 1.1.8.2 jruoho return a.zout_start;
2569 1.1.8.2 jruoho } else {
2570 1.1.8.2 jruoho FREE(a.zout_start);
2571 1.1.8.2 jruoho return NULL;
2572 1.1.8.2 jruoho }
2573 1.1.8.2 jruoho }
2574 1.1.8.2 jruoho
2575 1.1.8.2 jruoho int stbi_zlib_decode_noheader_buffer(char *obuffer, int olen, const char *ibuffer, int ilen)
2576 1.1.8.2 jruoho {
2577 1.1.8.2 jruoho zbuf a;
2578 1.1.8.2 jruoho a.zbuffer = (uint8 const *) ibuffer;
2579 1.1.8.2 jruoho a.zbuffer_end = (uint8 const *) ibuffer + ilen;
2580 1.1.8.2 jruoho if (do_zlib(&a, obuffer, olen, 0, 0))
2581 1.1.8.2 jruoho return (int) (a.zout - a.zout_start);
2582 1.1.8.2 jruoho else
2583 1.1.8.2 jruoho return -1;
2584 1.1.8.2 jruoho }
2585 1.1.8.2 jruoho
2586 1.1.8.2 jruoho // public domain "baseline" PNG decoder v0.10 Sean Barrett 2006-11-18
2587 1.1.8.2 jruoho // simple implementation
2588 1.1.8.2 jruoho // - only 8-bit samples
2589 1.1.8.2 jruoho // - no CRC checking
2590 1.1.8.2 jruoho // - allocates lots of intermediate memory
2591 1.1.8.2 jruoho // - avoids problem of streaming data between subsystems
2592 1.1.8.2 jruoho // - avoids explicit window management
2593 1.1.8.2 jruoho // performance
2594 1.1.8.2 jruoho // - uses stb_zlib, a PD zlib implementation with fast huffman decoding
2595 1.1.8.2 jruoho
2596 1.1.8.2 jruoho
2597 1.1.8.2 jruoho typedef struct
2598 1.1.8.2 jruoho {
2599 1.1.8.2 jruoho uint32 length;
2600 1.1.8.2 jruoho uint32 type;
2601 1.1.8.2 jruoho } chunk;
2602 1.1.8.2 jruoho
2603 1.1.8.2 jruoho #define PNG_TYPE(a,b,c,d) (((a) << 24) + ((b) << 16) + ((c) << 8) + (d))
2604 1.1.8.2 jruoho
2605 1.1.8.2 jruoho static chunk get_chunk_header(stbi *s)
2606 1.1.8.2 jruoho {
2607 1.1.8.2 jruoho chunk c;
2608 1.1.8.2 jruoho c.length = get32(s);
2609 1.1.8.2 jruoho c.type = get32(s);
2610 1.1.8.2 jruoho return c;
2611 1.1.8.2 jruoho }
2612 1.1.8.2 jruoho
2613 1.1.8.2 jruoho static int check_png_header(stbi *s)
2614 1.1.8.2 jruoho {
2615 1.1.8.2 jruoho static uint8 png_sig[8] = { 137,80,78,71,13,10,26,10 };
2616 1.1.8.2 jruoho int i;
2617 1.1.8.2 jruoho for (i=0; i < 8; ++i)
2618 1.1.8.2 jruoho if (get8(s) != png_sig[i]) return e("bad png sig","Not a PNG");
2619 1.1.8.2 jruoho return 1;
2620 1.1.8.2 jruoho }
2621 1.1.8.2 jruoho
2622 1.1.8.2 jruoho typedef struct
2623 1.1.8.2 jruoho {
2624 1.1.8.2 jruoho stbi s;
2625 1.1.8.2 jruoho uint8 *idata, *expanded, *out;
2626 1.1.8.2 jruoho } png;
2627 1.1.8.2 jruoho
2628 1.1.8.2 jruoho
2629 1.1.8.2 jruoho enum {
2630 1.1.8.2 jruoho F_none=0, F_sub=1, F_up=2, F_avg=3, F_paeth=4,
2631 1.1.8.2 jruoho F_avg_first, F_paeth_first
2632 1.1.8.2 jruoho };
2633 1.1.8.2 jruoho
2634 1.1.8.2 jruoho static uint8 first_row_filter[5] =
2635 1.1.8.2 jruoho {
2636 1.1.8.2 jruoho F_none, F_sub, F_none, F_avg_first, F_paeth_first
2637 1.1.8.2 jruoho };
2638 1.1.8.2 jruoho
2639 1.1.8.2 jruoho static int paeth(int a, int b, int c)
2640 1.1.8.2 jruoho {
2641 1.1.8.2 jruoho int p = a + b - c;
2642 1.1.8.2 jruoho int pa = abs(p-a);
2643 1.1.8.2 jruoho int pb = abs(p-b);
2644 1.1.8.2 jruoho int pc = abs(p-c);
2645 1.1.8.2 jruoho if (pa <= pb && pa <= pc) return a;
2646 1.1.8.2 jruoho if (pb <= pc) return b;
2647 1.1.8.2 jruoho return c;
2648 1.1.8.2 jruoho }
2649 1.1.8.2 jruoho
2650 1.1.8.2 jruoho // create the png data from post-deflated data
2651 1.1.8.2 jruoho static int create_png_image_raw(png *a, uint8 *raw, uint32 raw_len, int out_n, uint32 x, uint32 y)
2652 1.1.8.2 jruoho {
2653 1.1.8.2 jruoho stbi *s = &a->s;
2654 1.1.8.2 jruoho uint32 i,j,stride = x*out_n;
2655 1.1.8.2 jruoho int k;
2656 1.1.8.2 jruoho int img_n = s->img_n; // copy it into a local for later
2657 1.1.8.2 jruoho assert(out_n == s->img_n || out_n == s->img_n+1);
2658 1.1.8.2 jruoho if (stbi_png_partial) y = 1;
2659 1.1.8.2 jruoho a->out = (uint8 *) MALLOC(x * y * out_n);
2660 1.1.8.2 jruoho if (!a->out) return e("outofmem", "Out of memory");
2661 1.1.8.2 jruoho if (!stbi_png_partial) {
2662 1.1.8.2 jruoho if (s->img_x == x && s->img_y == y) {
2663 1.1.8.2 jruoho if (raw_len != (img_n * x + 1) * y) return e("not enough pixels","Corrupt PNG");
2664 1.1.8.2 jruoho } else { // interlaced:
2665 1.1.8.2 jruoho if (raw_len < (img_n * x + 1) * y) return e("not enough pixels","Corrupt PNG");
2666 1.1.8.2 jruoho }
2667 1.1.8.2 jruoho }
2668 1.1.8.2 jruoho for (j=0; j < y; ++j) {
2669 1.1.8.2 jruoho uint8 *cur = a->out + stride*j;
2670 1.1.8.2 jruoho uint8 *prior = cur - stride;
2671 1.1.8.2 jruoho int filter = *raw++;
2672 1.1.8.2 jruoho if (filter > 4) return e("invalid filter","Corrupt PNG");
2673 1.1.8.2 jruoho // if first row, use special filter that doesn't sample previous row
2674 1.1.8.2 jruoho if (j == 0) filter = first_row_filter[filter];
2675 1.1.8.2 jruoho // handle first pixel explicitly
2676 1.1.8.2 jruoho for (k=0; k < img_n; ++k) {
2677 1.1.8.2 jruoho switch (filter) {
2678 1.1.8.2 jruoho case F_none : cur[k] = raw[k]; break;
2679 1.1.8.2 jruoho case F_sub : cur[k] = raw[k]; break;
2680 1.1.8.2 jruoho case F_up : cur[k] = raw[k] + prior[k]; break;
2681 1.1.8.2 jruoho case F_avg : cur[k] = raw[k] + (prior[k]>>1); break;
2682 1.1.8.2 jruoho case F_paeth : cur[k] = (uint8) (raw[k] + paeth(0,prior[k],0)); break;
2683 1.1.8.2 jruoho case F_avg_first : cur[k] = raw[k]; break;
2684 1.1.8.2 jruoho case F_paeth_first: cur[k] = raw[k]; break;
2685 1.1.8.2 jruoho }
2686 1.1.8.2 jruoho }
2687 1.1.8.2 jruoho if (img_n != out_n) cur[img_n] = 255;
2688 1.1.8.2 jruoho raw += img_n;
2689 1.1.8.2 jruoho cur += out_n;
2690 1.1.8.2 jruoho prior += out_n;
2691 1.1.8.2 jruoho // this is a little gross, so that we don't switch per-pixel or per-component
2692 1.1.8.2 jruoho if (img_n == out_n) {
2693 1.1.8.2 jruoho #define CASE(f) \
2694 1.1.8.2 jruoho case f: \
2695 1.1.8.2 jruoho for (i=x-1; i >= 1; --i, raw+=img_n,cur+=img_n,prior+=img_n) \
2696 1.1.8.2 jruoho for (k=0; k < img_n; ++k)
2697 1.1.8.2 jruoho switch (filter) {
2698 1.1.8.2 jruoho CASE(F_none) cur[k] = raw[k]; break;
2699 1.1.8.2 jruoho CASE(F_sub) cur[k] = raw[k] + cur[k-img_n]; break;
2700 1.1.8.2 jruoho CASE(F_up) cur[k] = raw[k] + prior[k]; break;
2701 1.1.8.2 jruoho CASE(F_avg) cur[k] = raw[k] + ((prior[k] + cur[k-img_n])>>1); break;
2702 1.1.8.2 jruoho CASE(F_paeth) cur[k] = (uint8) (raw[k] + paeth(cur[k-img_n],prior[k],prior[k-img_n])); break;
2703 1.1.8.2 jruoho CASE(F_avg_first) cur[k] = raw[k] + (cur[k-img_n] >> 1); break;
2704 1.1.8.2 jruoho CASE(F_paeth_first) cur[k] = (uint8) (raw[k] + paeth(cur[k-img_n],0,0)); break;
2705 1.1.8.2 jruoho }
2706 1.1.8.2 jruoho #undef CASE
2707 1.1.8.2 jruoho } else {
2708 1.1.8.2 jruoho assert(img_n+1 == out_n);
2709 1.1.8.2 jruoho #define CASE(f) \
2710 1.1.8.2 jruoho case f: \
2711 1.1.8.2 jruoho for (i=x-1; i >= 1; --i, cur[img_n]=255,raw+=img_n,cur+=out_n,prior+=out_n) \
2712 1.1.8.2 jruoho for (k=0; k < img_n; ++k)
2713 1.1.8.2 jruoho switch (filter) {
2714 1.1.8.2 jruoho CASE(F_none) cur[k] = raw[k]; break;
2715 1.1.8.2 jruoho CASE(F_sub) cur[k] = raw[k] + cur[k-out_n]; break;
2716 1.1.8.2 jruoho CASE(F_up) cur[k] = raw[k] + prior[k]; break;
2717 1.1.8.2 jruoho CASE(F_avg) cur[k] = raw[k] + ((prior[k] + cur[k-out_n])>>1); break;
2718 1.1.8.2 jruoho CASE(F_paeth) cur[k] = (uint8) (raw[k] + paeth(cur[k-out_n],prior[k],prior[k-out_n])); break;
2719 1.1.8.2 jruoho CASE(F_avg_first) cur[k] = raw[k] + (cur[k-out_n] >> 1); break;
2720 1.1.8.2 jruoho CASE(F_paeth_first) cur[k] = (uint8) (raw[k] + paeth(cur[k-out_n],0,0)); break;
2721 1.1.8.2 jruoho }
2722 1.1.8.2 jruoho #undef CASE
2723 1.1.8.2 jruoho }
2724 1.1.8.2 jruoho }
2725 1.1.8.2 jruoho return 1;
2726 1.1.8.2 jruoho }
2727 1.1.8.2 jruoho
2728 1.1.8.2 jruoho static int create_png_image(png *a, uint8 *raw, uint32 raw_len, int out_n, int interlaced)
2729 1.1.8.2 jruoho {
2730 1.1.8.2 jruoho uint8 *final;
2731 1.1.8.2 jruoho int p;
2732 1.1.8.2 jruoho int save;
2733 1.1.8.2 jruoho if (!interlaced)
2734 1.1.8.2 jruoho return create_png_image_raw(a, raw, raw_len, out_n, a->s.img_x, a->s.img_y);
2735 1.1.8.2 jruoho save = stbi_png_partial;
2736 1.1.8.2 jruoho stbi_png_partial = 0;
2737 1.1.8.2 jruoho
2738 1.1.8.2 jruoho // de-interlacing
2739 1.1.8.2 jruoho final = (uint8 *) MALLOC(a->s.img_x * a->s.img_y * out_n);
2740 1.1.8.2 jruoho for (p=0; p < 7; ++p) {
2741 1.1.8.2 jruoho int xorig[] = { 0,4,0,2,0,1,0 };
2742 1.1.8.2 jruoho int yorig[] = { 0,0,4,0,2,0,1 };
2743 1.1.8.2 jruoho int xspc[] = { 8,8,4,4,2,2,1 };
2744 1.1.8.2 jruoho int yspc[] = { 8,8,8,4,4,2,2 };
2745 1.1.8.2 jruoho int i,j,x,y;
2746 1.1.8.2 jruoho // pass1_x[4] = 0, pass1_x[5] = 1, pass1_x[12] = 1
2747 1.1.8.2 jruoho x = (a->s.img_x - xorig[p] + xspc[p]-1) / xspc[p];
2748 1.1.8.2 jruoho y = (a->s.img_y - yorig[p] + yspc[p]-1) / yspc[p];
2749 1.1.8.2 jruoho if (x && y) {
2750 1.1.8.2 jruoho if (!create_png_image_raw(a, raw, raw_len, out_n, x, y)) {
2751 1.1.8.2 jruoho FREE(final);
2752 1.1.8.2 jruoho return 0;
2753 1.1.8.2 jruoho }
2754 1.1.8.2 jruoho for (j=0; j < y; ++j)
2755 1.1.8.2 jruoho for (i=0; i < x; ++i)
2756 1.1.8.2 jruoho memcpy(final + (j*yspc[p]+yorig[p])*a->s.img_x*out_n + (i*xspc[p]+xorig[p])*out_n,
2757 1.1.8.2 jruoho a->out + (j*x+i)*out_n, out_n);
2758 1.1.8.2 jruoho FREE(a->out);
2759 1.1.8.2 jruoho raw += (x*out_n+1)*y;
2760 1.1.8.2 jruoho raw_len -= (x*out_n+1)*y;
2761 1.1.8.2 jruoho }
2762 1.1.8.2 jruoho }
2763 1.1.8.2 jruoho a->out = final;
2764 1.1.8.2 jruoho
2765 1.1.8.2 jruoho stbi_png_partial = save;
2766 1.1.8.2 jruoho return 1;
2767 1.1.8.2 jruoho }
2768 1.1.8.2 jruoho
2769 1.1.8.2 jruoho static int compute_transparency(png *z, uint8 tc[3], int out_n)
2770 1.1.8.2 jruoho {
2771 1.1.8.2 jruoho stbi *s = &z->s;
2772 1.1.8.2 jruoho uint32 i, pixel_count = s->img_x * s->img_y;
2773 1.1.8.2 jruoho uint8 *p = z->out;
2774 1.1.8.2 jruoho
2775 1.1.8.2 jruoho // compute color-based transparency, assuming we've
2776 1.1.8.2 jruoho // already got 255 as the alpha value in the output
2777 1.1.8.2 jruoho assert(out_n == 2 || out_n == 4);
2778 1.1.8.2 jruoho
2779 1.1.8.2 jruoho if (out_n == 2) {
2780 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2781 1.1.8.2 jruoho p[1] = (p[0] == tc[0] ? 0 : 255);
2782 1.1.8.2 jruoho p += 2;
2783 1.1.8.2 jruoho }
2784 1.1.8.2 jruoho } else {
2785 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2786 1.1.8.2 jruoho if (p[0] == tc[0] && p[1] == tc[1] && p[2] == tc[2])
2787 1.1.8.2 jruoho p[3] = 0;
2788 1.1.8.2 jruoho p += 4;
2789 1.1.8.2 jruoho }
2790 1.1.8.2 jruoho }
2791 1.1.8.2 jruoho return 1;
2792 1.1.8.2 jruoho }
2793 1.1.8.2 jruoho
2794 1.1.8.2 jruoho static int expand_palette(png *a, uint8 *palette, int len, int pal_img_n)
2795 1.1.8.2 jruoho {
2796 1.1.8.2 jruoho uint32 i, pixel_count = a->s.img_x * a->s.img_y;
2797 1.1.8.2 jruoho uint8 *p, *temp_out, *orig = a->out;
2798 1.1.8.2 jruoho
2799 1.1.8.2 jruoho p = (uint8 *) MALLOC(pixel_count * pal_img_n);
2800 1.1.8.2 jruoho if (p == NULL) return e("outofmem", "Out of memory");
2801 1.1.8.2 jruoho
2802 1.1.8.2 jruoho // between here and FREE(out) below, exitting would leak
2803 1.1.8.2 jruoho temp_out = p;
2804 1.1.8.2 jruoho
2805 1.1.8.2 jruoho if (pal_img_n == 3) {
2806 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2807 1.1.8.2 jruoho int n = orig[i]*4;
2808 1.1.8.2 jruoho p[0] = palette[n ];
2809 1.1.8.2 jruoho p[1] = palette[n+1];
2810 1.1.8.2 jruoho p[2] = palette[n+2];
2811 1.1.8.2 jruoho p += 3;
2812 1.1.8.2 jruoho }
2813 1.1.8.2 jruoho } else {
2814 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2815 1.1.8.2 jruoho int n = orig[i]*4;
2816 1.1.8.2 jruoho p[0] = palette[n ];
2817 1.1.8.2 jruoho p[1] = palette[n+1];
2818 1.1.8.2 jruoho p[2] = palette[n+2];
2819 1.1.8.2 jruoho p[3] = palette[n+3];
2820 1.1.8.2 jruoho p += 4;
2821 1.1.8.2 jruoho }
2822 1.1.8.2 jruoho }
2823 1.1.8.2 jruoho FREE(a->out);
2824 1.1.8.2 jruoho a->out = temp_out;
2825 1.1.8.2 jruoho
2826 1.1.8.2 jruoho STBI_NOTUSED(len);
2827 1.1.8.2 jruoho
2828 1.1.8.2 jruoho return 1;
2829 1.1.8.2 jruoho }
2830 1.1.8.2 jruoho
2831 1.1.8.2 jruoho static int stbi_unpremultiply_on_load = 0;
2832 1.1.8.2 jruoho static int stbi_de_iphone_flag = 0;
2833 1.1.8.2 jruoho
2834 1.1.8.2 jruoho void stbi_set_unpremultiply_on_load(int flag_true_if_should_unpremultiply)
2835 1.1.8.2 jruoho {
2836 1.1.8.2 jruoho stbi_unpremultiply_on_load = flag_true_if_should_unpremultiply;
2837 1.1.8.2 jruoho }
2838 1.1.8.2 jruoho void stbi_convert_iphone_png_to_rgb(int flag_true_if_should_convert)
2839 1.1.8.2 jruoho {
2840 1.1.8.2 jruoho stbi_de_iphone_flag = flag_true_if_should_convert;
2841 1.1.8.2 jruoho }
2842 1.1.8.2 jruoho
2843 1.1.8.2 jruoho static void stbi_de_iphone(png *z)
2844 1.1.8.2 jruoho {
2845 1.1.8.2 jruoho stbi *s = &z->s;
2846 1.1.8.2 jruoho uint32 i, pixel_count = s->img_x * s->img_y;
2847 1.1.8.2 jruoho uint8 *p = z->out;
2848 1.1.8.2 jruoho
2849 1.1.8.2 jruoho if (s->img_out_n == 3) { // convert bgr to rgb
2850 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2851 1.1.8.2 jruoho uint8 t = p[0];
2852 1.1.8.2 jruoho p[0] = p[2];
2853 1.1.8.2 jruoho p[2] = t;
2854 1.1.8.2 jruoho p += 3;
2855 1.1.8.2 jruoho }
2856 1.1.8.2 jruoho } else {
2857 1.1.8.2 jruoho assert(s->img_out_n == 4);
2858 1.1.8.2 jruoho if (stbi_unpremultiply_on_load) {
2859 1.1.8.2 jruoho // convert bgr to rgb and unpremultiply
2860 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2861 1.1.8.2 jruoho uint8 a = p[3];
2862 1.1.8.2 jruoho uint8 t = p[0];
2863 1.1.8.2 jruoho if (a) {
2864 1.1.8.2 jruoho p[0] = p[2] * 255 / a;
2865 1.1.8.2 jruoho p[1] = p[1] * 255 / a;
2866 1.1.8.2 jruoho p[2] = t * 255 / a;
2867 1.1.8.2 jruoho } else {
2868 1.1.8.2 jruoho p[0] = p[2];
2869 1.1.8.2 jruoho p[2] = t;
2870 1.1.8.2 jruoho }
2871 1.1.8.2 jruoho p += 4;
2872 1.1.8.2 jruoho }
2873 1.1.8.2 jruoho } else {
2874 1.1.8.2 jruoho // convert bgr to rgb
2875 1.1.8.2 jruoho for (i=0; i < pixel_count; ++i) {
2876 1.1.8.2 jruoho uint8 t = p[0];
2877 1.1.8.2 jruoho p[0] = p[2];
2878 1.1.8.2 jruoho p[2] = t;
2879 1.1.8.2 jruoho p += 4;
2880 1.1.8.2 jruoho }
2881 1.1.8.2 jruoho }
2882 1.1.8.2 jruoho }
2883 1.1.8.2 jruoho }
2884 1.1.8.2 jruoho
2885 1.1.8.2 jruoho static int parse_png_file(png *z, int scan, int req_comp)
2886 1.1.8.2 jruoho {
2887 1.1.8.2 jruoho uint8 palette[1024], pal_img_n=0;
2888 1.1.8.2 jruoho uint8 has_trans=0, tc[3];
2889 1.1.8.2 jruoho uint32 ioff=0, idata_limit=0, i, pal_len=0;
2890 1.1.8.2 jruoho int first=1,k,interlace=0, iphone=0;
2891 1.1.8.2 jruoho stbi *s = &z->s;
2892 1.1.8.2 jruoho
2893 1.1.8.2 jruoho if (!check_png_header(s)) return 0;
2894 1.1.8.2 jruoho
2895 1.1.8.2 jruoho if (scan == SCAN_type) return 1;
2896 1.1.8.2 jruoho
2897 1.1.8.2 jruoho for (;;) {
2898 1.1.8.2 jruoho chunk c = get_chunk_header(s);
2899 1.1.8.2 jruoho switch (c.type) {
2900 1.1.8.2 jruoho case PNG_TYPE('C','g','B','I'):
2901 1.1.8.2 jruoho iphone = stbi_de_iphone_flag;
2902 1.1.8.2 jruoho skip(s, c.length);
2903 1.1.8.2 jruoho break;
2904 1.1.8.2 jruoho case PNG_TYPE('I','H','D','R'): {
2905 1.1.8.2 jruoho int depth,color,comp,filter;
2906 1.1.8.2 jruoho if (!first) return e("multiple IHDR","Corrupt PNG");
2907 1.1.8.2 jruoho first = 0;
2908 1.1.8.2 jruoho if (c.length != 13) return e("bad IHDR len","Corrupt PNG");
2909 1.1.8.2 jruoho s->img_x = get32(s); if (s->img_x > (1 << 24)) return e("too large","Very large image (corrupt?)");
2910 1.1.8.2 jruoho s->img_y = get32(s); if (s->img_y > (1 << 24)) return e("too large","Very large image (corrupt?)");
2911 1.1.8.2 jruoho depth = get8(s); if (depth != 8) return e("8bit only","PNG not supported: 8-bit only");
2912 1.1.8.2 jruoho color = get8(s); if (color > 6) return e("bad ctype","Corrupt PNG");
2913 1.1.8.2 jruoho if (color == 3) pal_img_n = 3; else if (color & 1) return e("bad ctype","Corrupt PNG");
2914 1.1.8.2 jruoho comp = get8(s); if (comp) return e("bad comp method","Corrupt PNG");
2915 1.1.8.2 jruoho filter= get8(s); if (filter) return e("bad filter method","Corrupt PNG");
2916 1.1.8.2 jruoho interlace = get8(s); if (interlace>1) return e("bad interlace method","Corrupt PNG");
2917 1.1.8.2 jruoho if (!s->img_x || !s->img_y) return e("0-pixel image","Corrupt PNG");
2918 1.1.8.2 jruoho if (!pal_img_n) {
2919 1.1.8.2 jruoho s->img_n = (color & 2 ? 3 : 1) + (color & 4 ? 1 : 0);
2920 1.1.8.2 jruoho if ((1 << 30) / s->img_x / s->img_n < s->img_y) return e("too large", "Image too large to decode");
2921 1.1.8.2 jruoho if (scan == SCAN_header) return 1;
2922 1.1.8.2 jruoho } else {
2923 1.1.8.2 jruoho // if paletted, then pal_n is our final components, and
2924 1.1.8.2 jruoho // img_n is # components to decompress/filter.
2925 1.1.8.2 jruoho s->img_n = 1;
2926 1.1.8.2 jruoho if ((1 << 30) / s->img_x / 4 < s->img_y) return e("too large","Corrupt PNG");
2927 1.1.8.2 jruoho // if SCAN_header, have to scan to see if we have a tRNS
2928 1.1.8.2 jruoho }
2929 1.1.8.2 jruoho break;
2930 1.1.8.2 jruoho }
2931 1.1.8.2 jruoho
2932 1.1.8.2 jruoho case PNG_TYPE('P','L','T','E'): {
2933 1.1.8.2 jruoho if (first) return e("first not IHDR", "Corrupt PNG");
2934 1.1.8.2 jruoho if (c.length > 256*3) return e("invalid PLTE","Corrupt PNG");
2935 1.1.8.2 jruoho pal_len = c.length / 3;
2936 1.1.8.2 jruoho if (pal_len * 3 != c.length) return e("invalid PLTE","Corrupt PNG");
2937 1.1.8.2 jruoho for (i=0; i < pal_len; ++i) {
2938 1.1.8.2 jruoho palette[i*4+0] = get8u(s);
2939 1.1.8.2 jruoho palette[i*4+1] = get8u(s);
2940 1.1.8.2 jruoho palette[i*4+2] = get8u(s);
2941 1.1.8.2 jruoho palette[i*4+3] = 255;
2942 1.1.8.2 jruoho }
2943 1.1.8.2 jruoho break;
2944 1.1.8.2 jruoho }
2945 1.1.8.2 jruoho
2946 1.1.8.2 jruoho case PNG_TYPE('t','R','N','S'): {
2947 1.1.8.2 jruoho if (first) return e("first not IHDR", "Corrupt PNG");
2948 1.1.8.2 jruoho if (z->idata) return e("tRNS after IDAT","Corrupt PNG");
2949 1.1.8.2 jruoho if (pal_img_n) {
2950 1.1.8.2 jruoho if (scan == SCAN_header) { s->img_n = 4; return 1; }
2951 1.1.8.2 jruoho if (pal_len == 0) return e("tRNS before PLTE","Corrupt PNG");
2952 1.1.8.2 jruoho if (c.length > pal_len) return e("bad tRNS len","Corrupt PNG");
2953 1.1.8.2 jruoho pal_img_n = 4;
2954 1.1.8.2 jruoho for (i=0; i < c.length; ++i)
2955 1.1.8.2 jruoho palette[i*4+3] = get8u(s);
2956 1.1.8.2 jruoho } else {
2957 1.1.8.2 jruoho if (!(s->img_n & 1)) return e("tRNS with alpha","Corrupt PNG");
2958 1.1.8.2 jruoho if (c.length != (uint32) s->img_n*2) return e("bad tRNS len","Corrupt PNG");
2959 1.1.8.2 jruoho has_trans = 1;
2960 1.1.8.2 jruoho for (k=0; k < s->img_n; ++k)
2961 1.1.8.2 jruoho tc[k] = (uint8) get16(s); // non 8-bit images will be larger
2962 1.1.8.2 jruoho }
2963 1.1.8.2 jruoho break;
2964 1.1.8.2 jruoho }
2965 1.1.8.2 jruoho
2966 1.1.8.2 jruoho case PNG_TYPE('I','D','A','T'): {
2967 1.1.8.2 jruoho if (first) return e("first not IHDR", "Corrupt PNG");
2968 1.1.8.2 jruoho if (pal_img_n && !pal_len) return e("no PLTE","Corrupt PNG");
2969 1.1.8.2 jruoho if (scan == SCAN_header) { s->img_n = pal_img_n; return 1; }
2970 1.1.8.2 jruoho if (ioff + c.length > idata_limit) {
2971 1.1.8.2 jruoho uint8 *p;
2972 1.1.8.2 jruoho if (idata_limit == 0) idata_limit = c.length > 4096 ? c.length : 4096;
2973 1.1.8.2 jruoho while (ioff + c.length > idata_limit)
2974 1.1.8.2 jruoho idata_limit *= 2;
2975 1.1.8.2 jruoho p = (uint8 *) REALLOC(z->idata, idata_limit); if (p == NULL) return e("outofmem", "Out of memory");
2976 1.1.8.2 jruoho z->idata = p;
2977 1.1.8.2 jruoho }
2978 1.1.8.2 jruoho if (!getn(s, z->idata+ioff,c.length)) return e("outofdata","Corrupt PNG");
2979 1.1.8.2 jruoho ioff += c.length;
2980 1.1.8.2 jruoho break;
2981 1.1.8.2 jruoho }
2982 1.1.8.2 jruoho
2983 1.1.8.2 jruoho case PNG_TYPE('I','E','N','D'): {
2984 1.1.8.2 jruoho uint32 raw_len;
2985 1.1.8.2 jruoho if (first) return e("first not IHDR", "Corrupt PNG");
2986 1.1.8.2 jruoho if (scan != SCAN_load) return 1;
2987 1.1.8.2 jruoho if (z->idata == NULL) return e("no IDAT","Corrupt PNG");
2988 1.1.8.2 jruoho z->expanded = (uint8 *) stbi_zlib_decode_malloc_guesssize_headerflag((char *) z->idata, ioff, 16384, (int *) &raw_len, !iphone);
2989 1.1.8.2 jruoho if (z->expanded == NULL) return 0; // zlib should set error
2990 1.1.8.2 jruoho FREE(z->idata); z->idata = NULL;
2991 1.1.8.2 jruoho if ((req_comp == s->img_n+1 && req_comp != 3 && !pal_img_n) || has_trans)
2992 1.1.8.2 jruoho s->img_out_n = s->img_n+1;
2993 1.1.8.2 jruoho else
2994 1.1.8.2 jruoho s->img_out_n = s->img_n;
2995 1.1.8.2 jruoho if (!create_png_image(z, z->expanded, raw_len, s->img_out_n, interlace)) return 0;
2996 1.1.8.2 jruoho if (has_trans)
2997 1.1.8.2 jruoho if (!compute_transparency(z, tc, s->img_out_n)) return 0;
2998 1.1.8.2 jruoho if (iphone && s->img_out_n > 2)
2999 1.1.8.2 jruoho stbi_de_iphone(z);
3000 1.1.8.2 jruoho if (pal_img_n) {
3001 1.1.8.2 jruoho // pal_img_n == 3 or 4
3002 1.1.8.2 jruoho s->img_n = pal_img_n; // record the actual colors we had
3003 1.1.8.2 jruoho s->img_out_n = pal_img_n;
3004 1.1.8.2 jruoho if (req_comp >= 3) s->img_out_n = req_comp;
3005 1.1.8.2 jruoho if (!expand_palette(z, palette, pal_len, s->img_out_n))
3006 1.1.8.2 jruoho return 0;
3007 1.1.8.2 jruoho }
3008 1.1.8.2 jruoho FREE(z->expanded); z->expanded = NULL;
3009 1.1.8.2 jruoho return 1;
3010 1.1.8.2 jruoho }
3011 1.1.8.2 jruoho
3012 1.1.8.2 jruoho default:
3013 1.1.8.2 jruoho // if critical, fail
3014 1.1.8.2 jruoho if (first) return e("first not IHDR", "Corrupt PNG");
3015 1.1.8.2 jruoho if ((c.type & (1 << 29)) == 0) {
3016 1.1.8.2 jruoho #ifndef STBI_NO_FAILURE_STRINGS
3017 1.1.8.2 jruoho // not threadsafe
3018 1.1.8.2 jruoho static char invalid_chunk[] = "XXXX chunk not known";
3019 1.1.8.2 jruoho invalid_chunk[0] = (uint8) (c.type >> 24);
3020 1.1.8.2 jruoho invalid_chunk[1] = (uint8) (c.type >> 16);
3021 1.1.8.2 jruoho invalid_chunk[2] = (uint8) (c.type >> 8);
3022 1.1.8.2 jruoho invalid_chunk[3] = (uint8) (c.type >> 0);
3023 1.1.8.2 jruoho #endif
3024 1.1.8.2 jruoho return e(invalid_chunk, "PNG not supported: unknown chunk type");
3025 1.1.8.2 jruoho }
3026 1.1.8.2 jruoho skip(s, c.length);
3027 1.1.8.2 jruoho break;
3028 1.1.8.2 jruoho }
3029 1.1.8.2 jruoho // end of chunk, read and skip CRC
3030 1.1.8.2 jruoho get32(s);
3031 1.1.8.2 jruoho }
3032 1.1.8.2 jruoho }
3033 1.1.8.2 jruoho
3034 1.1.8.2 jruoho static unsigned char *do_png(png *p, int *x, int *y, int *n, int req_comp)
3035 1.1.8.2 jruoho {
3036 1.1.8.2 jruoho unsigned char *result=NULL;
3037 1.1.8.2 jruoho p->expanded = NULL;
3038 1.1.8.2 jruoho p->idata = NULL;
3039 1.1.8.2 jruoho p->out = NULL;
3040 1.1.8.2 jruoho if (req_comp < 0 || req_comp > 4) return epuc("bad req_comp", "Internal error");
3041 1.1.8.2 jruoho if (parse_png_file(p, SCAN_load, req_comp)) {
3042 1.1.8.2 jruoho result = p->out;
3043 1.1.8.2 jruoho p->out = NULL;
3044 1.1.8.2 jruoho if (req_comp && req_comp != p->s.img_out_n) {
3045 1.1.8.2 jruoho result = convert_format(result, p->s.img_out_n, req_comp, p->s.img_x, p->s.img_y);
3046 1.1.8.2 jruoho p->s.img_out_n = req_comp;
3047 1.1.8.2 jruoho if (result == NULL) return result;
3048 1.1.8.2 jruoho }
3049 1.1.8.2 jruoho *x = p->s.img_x;
3050 1.1.8.2 jruoho *y = p->s.img_y;
3051 1.1.8.2 jruoho if (n) *n = p->s.img_n;
3052 1.1.8.2 jruoho }
3053 1.1.8.2 jruoho FREE(p->out); p->out = NULL;
3054 1.1.8.2 jruoho FREE(p->expanded); p->expanded = NULL;
3055 1.1.8.2 jruoho FREE(p->idata); p->idata = NULL;
3056 1.1.8.2 jruoho
3057 1.1.8.2 jruoho return result;
3058 1.1.8.2 jruoho }
3059 1.1.8.2 jruoho
3060 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3061 1.1.8.2 jruoho unsigned char *stbi_png_load_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
3062 1.1.8.2 jruoho {
3063 1.1.8.2 jruoho png p;
3064 1.1.8.2 jruoho start_file(&p.s, f);
3065 1.1.8.2 jruoho return do_png(&p, x,y,comp,req_comp);
3066 1.1.8.2 jruoho }
3067 1.1.8.2 jruoho
3068 1.1.8.2 jruoho unsigned char *stbi_png_load(char const *filename, int *x, int *y, int *comp, int req_comp)
3069 1.1.8.2 jruoho {
3070 1.1.8.2 jruoho unsigned char *data;
3071 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
3072 1.1.8.2 jruoho if (!f) return NULL;
3073 1.1.8.2 jruoho data = stbi_png_load_from_file(f,x,y,comp,req_comp);
3074 1.1.8.2 jruoho fclose(f);
3075 1.1.8.2 jruoho return data;
3076 1.1.8.2 jruoho }
3077 1.1.8.2 jruoho #endif
3078 1.1.8.2 jruoho
3079 1.1.8.2 jruoho unsigned char *stbi_png_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
3080 1.1.8.2 jruoho {
3081 1.1.8.2 jruoho png p;
3082 1.1.8.2 jruoho start_mem(&p.s, buffer,len);
3083 1.1.8.2 jruoho return do_png(&p, x,y,comp,req_comp);
3084 1.1.8.2 jruoho }
3085 1.1.8.2 jruoho
3086 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3087 1.1.8.2 jruoho int stbi_png_test_file(FILE *f)
3088 1.1.8.2 jruoho {
3089 1.1.8.2 jruoho png p;
3090 1.1.8.2 jruoho int n,r;
3091 1.1.8.2 jruoho n = ftell(f);
3092 1.1.8.2 jruoho start_file(&p.s, f);
3093 1.1.8.2 jruoho r = parse_png_file(&p, SCAN_type,STBI_default);
3094 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
3095 1.1.8.2 jruoho return r;
3096 1.1.8.2 jruoho }
3097 1.1.8.2 jruoho #endif
3098 1.1.8.2 jruoho
3099 1.1.8.2 jruoho int stbi_png_test_memory(stbi_uc const *buffer, int len)
3100 1.1.8.2 jruoho {
3101 1.1.8.2 jruoho png p;
3102 1.1.8.2 jruoho start_mem(&p.s, buffer, len);
3103 1.1.8.2 jruoho return parse_png_file(&p, SCAN_type,STBI_default);
3104 1.1.8.2 jruoho }
3105 1.1.8.2 jruoho
3106 1.1.8.2 jruoho static int stbi_png_info_raw(png *p, int *x, int *y, int *comp)
3107 1.1.8.2 jruoho {
3108 1.1.8.2 jruoho if (!parse_png_file(p, SCAN_header, 0))
3109 1.1.8.2 jruoho return 0;
3110 1.1.8.2 jruoho if (x) *x = p->s.img_x;
3111 1.1.8.2 jruoho if (y) *y = p->s.img_y;
3112 1.1.8.2 jruoho if (comp) *comp = p->s.img_n;
3113 1.1.8.2 jruoho return 1;
3114 1.1.8.2 jruoho }
3115 1.1.8.2 jruoho
3116 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3117 1.1.8.2 jruoho int stbi_png_info (char const *filename, int *x, int *y, int *comp)
3118 1.1.8.2 jruoho {
3119 1.1.8.2 jruoho int res;
3120 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
3121 1.1.8.2 jruoho if (!f) return 0;
3122 1.1.8.2 jruoho res = stbi_png_info_from_file(f, x, y, comp);
3123 1.1.8.2 jruoho fclose(f);
3124 1.1.8.2 jruoho return res;
3125 1.1.8.2 jruoho }
3126 1.1.8.2 jruoho
3127 1.1.8.2 jruoho int stbi_png_info_from_file(FILE *f, int *x, int *y, int *comp)
3128 1.1.8.2 jruoho {
3129 1.1.8.2 jruoho png p;
3130 1.1.8.2 jruoho int res;
3131 1.1.8.2 jruoho long n = ftell(f);
3132 1.1.8.2 jruoho start_file(&p.s, f);
3133 1.1.8.2 jruoho res = stbi_png_info_raw(&p, x, y, comp);
3134 1.1.8.2 jruoho fseek(f, n, SEEK_SET);
3135 1.1.8.2 jruoho return res;
3136 1.1.8.2 jruoho }
3137 1.1.8.2 jruoho #endif // !STBI_NO_STDIO
3138 1.1.8.2 jruoho
3139 1.1.8.2 jruoho int stbi_png_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp)
3140 1.1.8.2 jruoho {
3141 1.1.8.2 jruoho png p;
3142 1.1.8.2 jruoho start_mem(&p.s, buffer, len);
3143 1.1.8.2 jruoho return stbi_png_info_raw(&p, x, y, comp);
3144 1.1.8.2 jruoho }
3145 1.1.8.2 jruoho
3146 1.1.8.2 jruoho // Microsoft/Windows BMP image
3147 1.1.8.2 jruoho
3148 1.1.8.2 jruoho static int bmp_test(stbi *s)
3149 1.1.8.2 jruoho {
3150 1.1.8.2 jruoho int sz;
3151 1.1.8.2 jruoho if (get8(s) != 'B') return 0;
3152 1.1.8.2 jruoho if (get8(s) != 'M') return 0;
3153 1.1.8.2 jruoho get32le(s); // discard filesize
3154 1.1.8.2 jruoho get16le(s); // discard reserved
3155 1.1.8.2 jruoho get16le(s); // discard reserved
3156 1.1.8.2 jruoho get32le(s); // discard data offset
3157 1.1.8.2 jruoho sz = get32le(s);
3158 1.1.8.2 jruoho if (sz == 12 || sz == 40 || sz == 56 || sz == 108) return 1;
3159 1.1.8.2 jruoho return 0;
3160 1.1.8.2 jruoho }
3161 1.1.8.2 jruoho
3162 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3163 1.1.8.2 jruoho int stbi_bmp_test_file (FILE *f)
3164 1.1.8.2 jruoho {
3165 1.1.8.2 jruoho stbi s;
3166 1.1.8.2 jruoho int r,n = ftell(f);
3167 1.1.8.2 jruoho start_file(&s,f);
3168 1.1.8.2 jruoho r = bmp_test(&s);
3169 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
3170 1.1.8.2 jruoho return r;
3171 1.1.8.2 jruoho }
3172 1.1.8.2 jruoho #endif
3173 1.1.8.2 jruoho
3174 1.1.8.2 jruoho int stbi_bmp_test_memory (stbi_uc const *buffer, int len)
3175 1.1.8.2 jruoho {
3176 1.1.8.2 jruoho stbi s;
3177 1.1.8.2 jruoho start_mem(&s, buffer, len);
3178 1.1.8.2 jruoho return bmp_test(&s);
3179 1.1.8.2 jruoho }
3180 1.1.8.2 jruoho
3181 1.1.8.2 jruoho // returns 0..31 for the highest set bit
3182 1.1.8.2 jruoho static int high_bit(unsigned int z)
3183 1.1.8.2 jruoho {
3184 1.1.8.2 jruoho int n=0;
3185 1.1.8.2 jruoho if (z == 0) return -1;
3186 1.1.8.2 jruoho if (z >= 0x10000) n += 16, z >>= 16;
3187 1.1.8.2 jruoho if (z >= 0x00100) n += 8, z >>= 8;
3188 1.1.8.2 jruoho if (z >= 0x00010) n += 4, z >>= 4;
3189 1.1.8.2 jruoho if (z >= 0x00004) n += 2, z >>= 2;
3190 1.1.8.2 jruoho if (z >= 0x00002) n += 1, z >>= 1;
3191 1.1.8.2 jruoho return n;
3192 1.1.8.2 jruoho }
3193 1.1.8.2 jruoho
3194 1.1.8.2 jruoho static int bitcount(unsigned int a)
3195 1.1.8.2 jruoho {
3196 1.1.8.2 jruoho a = (a & 0x55555555) + ((a >> 1) & 0x55555555); // max 2
3197 1.1.8.2 jruoho a = (a & 0x33333333) + ((a >> 2) & 0x33333333); // max 4
3198 1.1.8.2 jruoho a = (a + (a >> 4)) & 0x0f0f0f0f; // max 8 per 4, now 8 bits
3199 1.1.8.2 jruoho a = (a + (a >> 8)); // max 16 per 8 bits
3200 1.1.8.2 jruoho a = (a + (a >> 16)); // max 32 per 8 bits
3201 1.1.8.2 jruoho return a & 0xff;
3202 1.1.8.2 jruoho }
3203 1.1.8.2 jruoho
3204 1.1.8.2 jruoho static int shiftsigned(int v, int shift, int bits)
3205 1.1.8.2 jruoho {
3206 1.1.8.2 jruoho int result;
3207 1.1.8.2 jruoho int z=0;
3208 1.1.8.2 jruoho
3209 1.1.8.2 jruoho if (shift < 0) v <<= -shift;
3210 1.1.8.2 jruoho else v >>= shift;
3211 1.1.8.2 jruoho result = v;
3212 1.1.8.2 jruoho
3213 1.1.8.2 jruoho z = bits;
3214 1.1.8.2 jruoho while (z < 8) {
3215 1.1.8.2 jruoho result += v >> z;
3216 1.1.8.2 jruoho z += bits;
3217 1.1.8.2 jruoho }
3218 1.1.8.2 jruoho return result;
3219 1.1.8.2 jruoho }
3220 1.1.8.2 jruoho
3221 1.1.8.2 jruoho static stbi_uc *bmp_load(stbi *s, int *x, int *y, int *comp, int req_comp)
3222 1.1.8.2 jruoho {
3223 1.1.8.2 jruoho uint8 *out;
3224 1.1.8.2 jruoho unsigned int mr=0,mg=0,mb=0,ma=0, fake_a=0;
3225 1.1.8.2 jruoho stbi_uc pal[256][4];
3226 1.1.8.2 jruoho int psize=0,i,j,compress=0,width;
3227 1.1.8.2 jruoho int bpp, flip_vertically, pad, target, offset, hsz;
3228 1.1.8.2 jruoho if (get8(s) != 'B' || get8(s) != 'M') return epuc("not BMP", "Corrupt BMP");
3229 1.1.8.2 jruoho get32le(s); // discard filesize
3230 1.1.8.2 jruoho get16le(s); // discard reserved
3231 1.1.8.2 jruoho get16le(s); // discard reserved
3232 1.1.8.2 jruoho offset = get32le(s);
3233 1.1.8.2 jruoho hsz = get32le(s);
3234 1.1.8.2 jruoho if (hsz != 12 && hsz != 40 && hsz != 56 && hsz != 108) return epuc("unknown BMP", "BMP type not supported: unknown");
3235 1.1.8.2 jruoho if (hsz == 12) {
3236 1.1.8.2 jruoho s->img_x = get16le(s);
3237 1.1.8.2 jruoho s->img_y = get16le(s);
3238 1.1.8.2 jruoho } else {
3239 1.1.8.2 jruoho s->img_x = get32le(s);
3240 1.1.8.2 jruoho s->img_y = get32le(s);
3241 1.1.8.2 jruoho }
3242 1.1.8.2 jruoho if (get16le(s) != 1) return epuc("bad BMP", "bad BMP");
3243 1.1.8.2 jruoho bpp = get16le(s);
3244 1.1.8.2 jruoho if (bpp == 1) return epuc("monochrome", "BMP type not supported: 1-bit");
3245 1.1.8.2 jruoho flip_vertically = ((int) s->img_y) > 0;
3246 1.1.8.2 jruoho s->img_y = abs((int) s->img_y);
3247 1.1.8.2 jruoho if (hsz == 12) {
3248 1.1.8.2 jruoho if (bpp < 24)
3249 1.1.8.2 jruoho psize = (offset - 14 - 24) / 3;
3250 1.1.8.2 jruoho } else {
3251 1.1.8.2 jruoho compress = get32le(s);
3252 1.1.8.2 jruoho if (compress == 1 || compress == 2) return epuc("BMP RLE", "BMP type not supported: RLE");
3253 1.1.8.2 jruoho get32le(s); // discard sizeof
3254 1.1.8.2 jruoho get32le(s); // discard hres
3255 1.1.8.2 jruoho get32le(s); // discard vres
3256 1.1.8.2 jruoho get32le(s); // discard colorsused
3257 1.1.8.2 jruoho get32le(s); // discard max important
3258 1.1.8.2 jruoho if (hsz == 40 || hsz == 56) {
3259 1.1.8.2 jruoho if (hsz == 56) {
3260 1.1.8.2 jruoho get32le(s);
3261 1.1.8.2 jruoho get32le(s);
3262 1.1.8.2 jruoho get32le(s);
3263 1.1.8.2 jruoho get32le(s);
3264 1.1.8.2 jruoho }
3265 1.1.8.2 jruoho if (bpp == 16 || bpp == 32) {
3266 1.1.8.2 jruoho mr = mg = mb = 0;
3267 1.1.8.2 jruoho if (compress == 0) {
3268 1.1.8.2 jruoho if (bpp == 32) {
3269 1.1.8.2 jruoho mr = 0xffu << 16;
3270 1.1.8.2 jruoho mg = 0xffu << 8;
3271 1.1.8.2 jruoho mb = 0xffu << 0;
3272 1.1.8.2 jruoho ma = 0xffu << 24;
3273 1.1.8.2 jruoho fake_a = 1; // @TODO: check for cases like alpha value is all 0 and switch it to 255
3274 1.1.8.2 jruoho } else {
3275 1.1.8.2 jruoho mr = 31u << 10;
3276 1.1.8.2 jruoho mg = 31u << 5;
3277 1.1.8.2 jruoho mb = 31u << 0;
3278 1.1.8.2 jruoho }
3279 1.1.8.2 jruoho } else if (compress == 3) {
3280 1.1.8.2 jruoho mr = get32le(s);
3281 1.1.8.2 jruoho mg = get32le(s);
3282 1.1.8.2 jruoho mb = get32le(s);
3283 1.1.8.2 jruoho // not documented, but generated by photoshop and handled by mspaint
3284 1.1.8.2 jruoho if (mr == mg && mg == mb) {
3285 1.1.8.2 jruoho // ?!?!?
3286 1.1.8.2 jruoho return epuc("bad BMP", "bad BMP");
3287 1.1.8.2 jruoho }
3288 1.1.8.2 jruoho } else
3289 1.1.8.2 jruoho return epuc("bad BMP", "bad BMP");
3290 1.1.8.2 jruoho }
3291 1.1.8.2 jruoho } else {
3292 1.1.8.2 jruoho assert(hsz == 108);
3293 1.1.8.2 jruoho mr = get32le(s);
3294 1.1.8.2 jruoho mg = get32le(s);
3295 1.1.8.2 jruoho mb = get32le(s);
3296 1.1.8.2 jruoho ma = get32le(s);
3297 1.1.8.2 jruoho get32le(s); // discard color space
3298 1.1.8.2 jruoho for (i=0; i < 12; ++i)
3299 1.1.8.2 jruoho get32le(s); // discard color space parameters
3300 1.1.8.2 jruoho }
3301 1.1.8.2 jruoho if (bpp < 16)
3302 1.1.8.2 jruoho psize = (offset - 14 - hsz) >> 2;
3303 1.1.8.2 jruoho }
3304 1.1.8.2 jruoho s->img_n = ma ? 4 : 3;
3305 1.1.8.2 jruoho if (req_comp && req_comp >= 3) // we can directly decode 3 or 4
3306 1.1.8.2 jruoho target = req_comp;
3307 1.1.8.2 jruoho else
3308 1.1.8.2 jruoho target = s->img_n; // if they want monochrome, we'll post-convert
3309 1.1.8.2 jruoho out = (stbi_uc *) MALLOC(target * s->img_x * s->img_y);
3310 1.1.8.2 jruoho if (!out) return epuc("outofmem", "Out of memory");
3311 1.1.8.2 jruoho if (bpp < 16) {
3312 1.1.8.2 jruoho int z=0;
3313 1.1.8.2 jruoho if (psize == 0 || psize > 256) { FREE(out); return epuc("invalid", "Corrupt BMP"); }
3314 1.1.8.2 jruoho for (i=0; i < psize; ++i) {
3315 1.1.8.2 jruoho pal[i][2] = get8u(s);
3316 1.1.8.2 jruoho pal[i][1] = get8u(s);
3317 1.1.8.2 jruoho pal[i][0] = get8u(s);
3318 1.1.8.2 jruoho if (hsz != 12) get8(s);
3319 1.1.8.2 jruoho pal[i][3] = 255;
3320 1.1.8.2 jruoho }
3321 1.1.8.2 jruoho skip(s, offset - 14 - hsz - psize * (hsz == 12 ? 3 : 4));
3322 1.1.8.2 jruoho if (bpp == 4) width = (s->img_x + 1) >> 1;
3323 1.1.8.2 jruoho else if (bpp == 8) width = s->img_x;
3324 1.1.8.2 jruoho else { FREE(out); return epuc("bad bpp", "Corrupt BMP"); }
3325 1.1.8.2 jruoho pad = (-width)&3;
3326 1.1.8.2 jruoho for (j=0; j < (int) s->img_y; ++j) {
3327 1.1.8.2 jruoho for (i=0; i < (int) s->img_x; i += 2) {
3328 1.1.8.2 jruoho int v=get8(s),v2=0;
3329 1.1.8.2 jruoho if (bpp == 4) {
3330 1.1.8.2 jruoho v2 = v & 15;
3331 1.1.8.2 jruoho v >>= 4;
3332 1.1.8.2 jruoho }
3333 1.1.8.2 jruoho out[z++] = pal[v][0];
3334 1.1.8.2 jruoho out[z++] = pal[v][1];
3335 1.1.8.2 jruoho out[z++] = pal[v][2];
3336 1.1.8.2 jruoho if (target == 4) out[z++] = 255;
3337 1.1.8.2 jruoho if (i+1 == (int) s->img_x) break;
3338 1.1.8.2 jruoho v = (bpp == 8) ? get8(s) : v2;
3339 1.1.8.2 jruoho out[z++] = pal[v][0];
3340 1.1.8.2 jruoho out[z++] = pal[v][1];
3341 1.1.8.2 jruoho out[z++] = pal[v][2];
3342 1.1.8.2 jruoho if (target == 4) out[z++] = 255;
3343 1.1.8.2 jruoho }
3344 1.1.8.2 jruoho skip(s, pad);
3345 1.1.8.2 jruoho }
3346 1.1.8.2 jruoho } else {
3347 1.1.8.2 jruoho int rshift=0,gshift=0,bshift=0,ashift=0,rcount=0,gcount=0,bcount=0,acount=0;
3348 1.1.8.2 jruoho int z = 0;
3349 1.1.8.2 jruoho int easy=0;
3350 1.1.8.2 jruoho skip(s, offset - 14 - hsz);
3351 1.1.8.2 jruoho if (bpp == 24) width = 3 * s->img_x;
3352 1.1.8.2 jruoho else if (bpp == 16) width = 2*s->img_x;
3353 1.1.8.2 jruoho else /* bpp = 32 and pad = 0 */ width=0;
3354 1.1.8.2 jruoho pad = (-width) & 3;
3355 1.1.8.2 jruoho if (bpp == 24) {
3356 1.1.8.2 jruoho easy = 1;
3357 1.1.8.2 jruoho } else if (bpp == 32) {
3358 1.1.8.2 jruoho if (mb == 0xff && mg == 0xff00 && mr == 0xff000000 && ma == 0xff000000)
3359 1.1.8.2 jruoho easy = 2;
3360 1.1.8.2 jruoho }
3361 1.1.8.2 jruoho if (!easy) {
3362 1.1.8.2 jruoho if (!mr || !mg || !mb) return epuc("bad masks", "Corrupt BMP");
3363 1.1.8.2 jruoho // right shift amt to put high bit in position #7
3364 1.1.8.2 jruoho rshift = high_bit(mr)-7; rcount = bitcount(mr);
3365 1.1.8.2 jruoho gshift = high_bit(mg)-7; gcount = bitcount(mr);
3366 1.1.8.2 jruoho bshift = high_bit(mb)-7; bcount = bitcount(mr);
3367 1.1.8.2 jruoho ashift = high_bit(ma)-7; acount = bitcount(mr);
3368 1.1.8.2 jruoho }
3369 1.1.8.2 jruoho for (j=0; j < (int) s->img_y; ++j) {
3370 1.1.8.2 jruoho if (easy) {
3371 1.1.8.2 jruoho for (i=0; i < (int) s->img_x; ++i) {
3372 1.1.8.2 jruoho int a;
3373 1.1.8.2 jruoho out[z+2] = get8u(s);
3374 1.1.8.2 jruoho out[z+1] = get8u(s);
3375 1.1.8.2 jruoho out[z+0] = get8u(s);
3376 1.1.8.2 jruoho z += 3;
3377 1.1.8.2 jruoho a = (easy == 2 ? get8(s) : 255);
3378 1.1.8.2 jruoho if (target == 4) out[z++] = (uint8) a;
3379 1.1.8.2 jruoho }
3380 1.1.8.2 jruoho } else {
3381 1.1.8.2 jruoho for (i=0; i < (int) s->img_x; ++i) {
3382 1.1.8.2 jruoho uint32 v = (bpp == 16 ? get16le(s) : get32le(s));
3383 1.1.8.2 jruoho int a;
3384 1.1.8.2 jruoho out[z++] = (uint8) shiftsigned(v & mr, rshift, rcount);
3385 1.1.8.2 jruoho out[z++] = (uint8) shiftsigned(v & mg, gshift, gcount);
3386 1.1.8.2 jruoho out[z++] = (uint8) shiftsigned(v & mb, bshift, bcount);
3387 1.1.8.2 jruoho a = (ma ? shiftsigned(v & ma, ashift, acount) : 255);
3388 1.1.8.2 jruoho if (target == 4) out[z++] = (uint8) a;
3389 1.1.8.2 jruoho }
3390 1.1.8.2 jruoho }
3391 1.1.8.2 jruoho skip(s, pad);
3392 1.1.8.2 jruoho }
3393 1.1.8.2 jruoho }
3394 1.1.8.2 jruoho if (flip_vertically) {
3395 1.1.8.2 jruoho stbi_uc t;
3396 1.1.8.2 jruoho for (j=0; j < (int) s->img_y>>1; ++j) {
3397 1.1.8.2 jruoho stbi_uc *p1 = out + j *s->img_x*target;
3398 1.1.8.2 jruoho stbi_uc *p2 = out + (s->img_y-1-j)*s->img_x*target;
3399 1.1.8.2 jruoho for (i=0; i < (int) s->img_x*target; ++i) {
3400 1.1.8.2 jruoho t = p1[i], p1[i] = p2[i], p2[i] = t;
3401 1.1.8.2 jruoho }
3402 1.1.8.2 jruoho }
3403 1.1.8.2 jruoho }
3404 1.1.8.2 jruoho
3405 1.1.8.2 jruoho if (req_comp && req_comp != target) {
3406 1.1.8.2 jruoho out = convert_format(out, target, req_comp, s->img_x, s->img_y);
3407 1.1.8.2 jruoho if (out == NULL) return out; // convert_format frees input on failure
3408 1.1.8.2 jruoho }
3409 1.1.8.2 jruoho
3410 1.1.8.2 jruoho *x = s->img_x;
3411 1.1.8.2 jruoho *y = s->img_y;
3412 1.1.8.2 jruoho if (comp) *comp = target;
3413 1.1.8.2 jruoho return out;
3414 1.1.8.2 jruoho }
3415 1.1.8.2 jruoho
3416 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3417 1.1.8.2 jruoho stbi_uc *stbi_bmp_load (char const *filename, int *x, int *y, int *comp, int req_comp)
3418 1.1.8.2 jruoho {
3419 1.1.8.2 jruoho stbi_uc *data;
3420 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
3421 1.1.8.2 jruoho if (!f) return NULL;
3422 1.1.8.2 jruoho data = stbi_bmp_load_from_file(f, x,y,comp,req_comp);
3423 1.1.8.2 jruoho fclose(f);
3424 1.1.8.2 jruoho return data;
3425 1.1.8.2 jruoho }
3426 1.1.8.2 jruoho
3427 1.1.8.2 jruoho stbi_uc *stbi_bmp_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp)
3428 1.1.8.2 jruoho {
3429 1.1.8.2 jruoho stbi s;
3430 1.1.8.2 jruoho start_file(&s, f);
3431 1.1.8.2 jruoho return bmp_load(&s, x,y,comp,req_comp);
3432 1.1.8.2 jruoho }
3433 1.1.8.2 jruoho #endif
3434 1.1.8.2 jruoho
3435 1.1.8.2 jruoho stbi_uc *stbi_bmp_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
3436 1.1.8.2 jruoho {
3437 1.1.8.2 jruoho stbi s;
3438 1.1.8.2 jruoho start_mem(&s, buffer, len);
3439 1.1.8.2 jruoho return bmp_load(&s, x,y,comp,req_comp);
3440 1.1.8.2 jruoho }
3441 1.1.8.2 jruoho
3442 1.1.8.2 jruoho // Targa Truevision - TGA
3443 1.1.8.2 jruoho // by Jonathan Dummer
3444 1.1.8.2 jruoho
3445 1.1.8.2 jruoho static int tga_info(stbi *s, int *x, int *y, int *comp)
3446 1.1.8.2 jruoho {
3447 1.1.8.2 jruoho int tga_w, tga_h, tga_comp;
3448 1.1.8.2 jruoho int sz;
3449 1.1.8.2 jruoho get8u(s); // discard Offset
3450 1.1.8.2 jruoho sz = get8u(s); // color type
3451 1.1.8.2 jruoho if( sz > 1 ) return 0; // only RGB or indexed allowed
3452 1.1.8.2 jruoho sz = get8u(s); // image type
3453 1.1.8.2 jruoho // only RGB or grey allowed, +/- RLE
3454 1.1.8.2 jruoho if ((sz != 1) && (sz != 2) && (sz != 3) && (sz != 9) && (sz != 10) && (sz != 11)) return 0;
3455 1.1.8.2 jruoho get16le(s); // discard palette start
3456 1.1.8.2 jruoho get16le(s); // discard palette length
3457 1.1.8.2 jruoho get8(s); // discard bits per palette color entry
3458 1.1.8.2 jruoho get16le(s); // discard x origin
3459 1.1.8.2 jruoho get16le(s); // discard y origin
3460 1.1.8.2 jruoho tga_w = get16le(s);
3461 1.1.8.2 jruoho if( tga_w < 1 ) return 0; // test width
3462 1.1.8.2 jruoho tga_h = get16le(s);
3463 1.1.8.2 jruoho if( tga_h < 1 ) return 0; // test height
3464 1.1.8.2 jruoho sz = get8(s); // bits per pixel
3465 1.1.8.2 jruoho // only RGB or RGBA or grey allowed
3466 1.1.8.2 jruoho if ((sz != 8) && (sz != 16) && (sz != 24) && (sz != 32)) return 0;
3467 1.1.8.2 jruoho tga_comp = sz;
3468 1.1.8.2 jruoho if (x) *x = tga_w;
3469 1.1.8.2 jruoho if (y) *y = tga_h;
3470 1.1.8.2 jruoho if (comp) *comp = tga_comp / 8;
3471 1.1.8.2 jruoho return 1; // seems to have passed everything
3472 1.1.8.2 jruoho }
3473 1.1.8.2 jruoho
3474 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3475 1.1.8.2 jruoho int stbi_tga_info_from_file(FILE *f, int *x, int *y, int *comp)
3476 1.1.8.2 jruoho {
3477 1.1.8.2 jruoho stbi s;
3478 1.1.8.2 jruoho int r;
3479 1.1.8.2 jruoho long n = ftell(f);
3480 1.1.8.2 jruoho start_file(&s, f);
3481 1.1.8.2 jruoho r = tga_info(&s, x, y, comp);
3482 1.1.8.2 jruoho fseek(f, n, SEEK_SET);
3483 1.1.8.2 jruoho return r;
3484 1.1.8.2 jruoho }
3485 1.1.8.2 jruoho #endif
3486 1.1.8.2 jruoho
3487 1.1.8.2 jruoho int stbi_tga_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp)
3488 1.1.8.2 jruoho {
3489 1.1.8.2 jruoho stbi s;
3490 1.1.8.2 jruoho start_mem(&s, buffer, len);
3491 1.1.8.2 jruoho return tga_info(&s, x, y, comp);
3492 1.1.8.2 jruoho }
3493 1.1.8.2 jruoho
3494 1.1.8.2 jruoho static int tga_test(stbi *s)
3495 1.1.8.2 jruoho {
3496 1.1.8.2 jruoho int sz;
3497 1.1.8.2 jruoho get8u(s); // discard Offset
3498 1.1.8.2 jruoho sz = get8u(s); // color type
3499 1.1.8.2 jruoho if ( sz > 1 ) return 0; // only RGB or indexed allowed
3500 1.1.8.2 jruoho sz = get8u(s); // image type
3501 1.1.8.2 jruoho if ( (sz != 1) && (sz != 2) && (sz != 3) && (sz != 9) && (sz != 10) && (sz != 11) ) return 0; // only RGB or grey allowed, +/- RLE
3502 1.1.8.2 jruoho get16(s); // discard palette start
3503 1.1.8.2 jruoho get16(s); // discard palette length
3504 1.1.8.2 jruoho get8(s); // discard bits per palette color entry
3505 1.1.8.2 jruoho get16(s); // discard x origin
3506 1.1.8.2 jruoho get16(s); // discard y origin
3507 1.1.8.2 jruoho if ( get16(s) < 1 ) return 0; // test width
3508 1.1.8.2 jruoho if ( get16(s) < 1 ) return 0; // test height
3509 1.1.8.2 jruoho sz = get8(s); // bits per pixel
3510 1.1.8.2 jruoho if ( (sz != 8) && (sz != 16) && (sz != 24) && (sz != 32) ) return 0; // only RGB or RGBA or grey allowed
3511 1.1.8.2 jruoho return 1; // seems to have passed everything
3512 1.1.8.2 jruoho }
3513 1.1.8.2 jruoho
3514 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3515 1.1.8.2 jruoho int stbi_tga_test_file (FILE *f)
3516 1.1.8.2 jruoho {
3517 1.1.8.2 jruoho stbi s;
3518 1.1.8.2 jruoho int r,n = ftell(f);
3519 1.1.8.2 jruoho start_file(&s, f);
3520 1.1.8.2 jruoho r = tga_test(&s);
3521 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
3522 1.1.8.2 jruoho return r;
3523 1.1.8.2 jruoho }
3524 1.1.8.2 jruoho #endif
3525 1.1.8.2 jruoho
3526 1.1.8.2 jruoho int stbi_tga_test_memory (stbi_uc const *buffer, int len)
3527 1.1.8.2 jruoho {
3528 1.1.8.2 jruoho stbi s;
3529 1.1.8.2 jruoho start_mem(&s, buffer, len);
3530 1.1.8.2 jruoho return tga_test(&s);
3531 1.1.8.2 jruoho }
3532 1.1.8.2 jruoho
3533 1.1.8.2 jruoho static stbi_uc *tga_load(stbi *s, int *x, int *y, int *comp, int req_comp)
3534 1.1.8.2 jruoho {
3535 1.1.8.2 jruoho // read in the TGA header stuff
3536 1.1.8.2 jruoho int tga_offset = get8u(s);
3537 1.1.8.2 jruoho int tga_indexed = get8u(s);
3538 1.1.8.2 jruoho int tga_image_type = get8u(s);
3539 1.1.8.2 jruoho int tga_is_RLE = 0;
3540 1.1.8.2 jruoho int tga_palette_start = get16le(s);
3541 1.1.8.2 jruoho int tga_palette_len = get16le(s);
3542 1.1.8.2 jruoho int tga_palette_bits = get8u(s);
3543 1.1.8.2 jruoho int tga_x_origin = get16le(s);
3544 1.1.8.2 jruoho int tga_y_origin = get16le(s);
3545 1.1.8.2 jruoho int tga_width = get16le(s);
3546 1.1.8.2 jruoho int tga_height = get16le(s);
3547 1.1.8.2 jruoho int tga_bits_per_pixel = get8u(s);
3548 1.1.8.2 jruoho int tga_inverted = get8u(s);
3549 1.1.8.2 jruoho // image data
3550 1.1.8.2 jruoho unsigned char *tga_data;
3551 1.1.8.2 jruoho unsigned char *tga_palette = NULL;
3552 1.1.8.2 jruoho int i, j;
3553 1.1.8.2 jruoho unsigned char raw_data[4];
3554 1.1.8.2 jruoho unsigned char trans_data[4];
3555 1.1.8.2 jruoho int RLE_count = 0;
3556 1.1.8.2 jruoho int RLE_repeating = 0;
3557 1.1.8.2 jruoho int read_next_pixel = 1;
3558 1.1.8.2 jruoho
3559 1.1.8.2 jruoho // do a tiny bit of precessing
3560 1.1.8.2 jruoho if ( tga_image_type >= 8 )
3561 1.1.8.2 jruoho {
3562 1.1.8.2 jruoho tga_image_type -= 8;
3563 1.1.8.2 jruoho tga_is_RLE = 1;
3564 1.1.8.2 jruoho }
3565 1.1.8.2 jruoho /* int tga_alpha_bits = tga_inverted & 15; */
3566 1.1.8.2 jruoho tga_inverted = 1 - ((tga_inverted >> 5) & 1);
3567 1.1.8.2 jruoho
3568 1.1.8.2 jruoho // error check
3569 1.1.8.2 jruoho if ( //(tga_indexed) ||
3570 1.1.8.2 jruoho (tga_width < 1) || (tga_height < 1) ||
3571 1.1.8.2 jruoho (tga_image_type < 1) || (tga_image_type > 3) ||
3572 1.1.8.2 jruoho ((tga_bits_per_pixel != 8) && (tga_bits_per_pixel != 16) &&
3573 1.1.8.2 jruoho (tga_bits_per_pixel != 24) && (tga_bits_per_pixel != 32))
3574 1.1.8.2 jruoho )
3575 1.1.8.2 jruoho {
3576 1.1.8.2 jruoho return NULL;
3577 1.1.8.2 jruoho }
3578 1.1.8.2 jruoho
3579 1.1.8.2 jruoho // If I'm paletted, then I'll use the number of bits from the palette
3580 1.1.8.2 jruoho if ( tga_indexed )
3581 1.1.8.2 jruoho {
3582 1.1.8.2 jruoho tga_bits_per_pixel = tga_palette_bits;
3583 1.1.8.2 jruoho }
3584 1.1.8.2 jruoho
3585 1.1.8.2 jruoho // tga info
3586 1.1.8.2 jruoho *x = tga_width;
3587 1.1.8.2 jruoho *y = tga_height;
3588 1.1.8.2 jruoho if ( (req_comp < 1) || (req_comp > 4) )
3589 1.1.8.2 jruoho {
3590 1.1.8.2 jruoho // just use whatever the file was
3591 1.1.8.2 jruoho req_comp = tga_bits_per_pixel / 8;
3592 1.1.8.2 jruoho *comp = req_comp;
3593 1.1.8.2 jruoho } else
3594 1.1.8.2 jruoho {
3595 1.1.8.2 jruoho // force a new number of components
3596 1.1.8.2 jruoho *comp = tga_bits_per_pixel/8;
3597 1.1.8.2 jruoho }
3598 1.1.8.2 jruoho tga_data = (unsigned char*)MALLOC( tga_width * tga_height * req_comp );
3599 1.1.8.2 jruoho
3600 1.1.8.2 jruoho // skip to the data's starting position (offset usually = 0)
3601 1.1.8.2 jruoho skip(s, tga_offset );
3602 1.1.8.2 jruoho // do I need to load a palette?
3603 1.1.8.2 jruoho if ( tga_indexed )
3604 1.1.8.2 jruoho {
3605 1.1.8.2 jruoho // any data to skip? (offset usually = 0)
3606 1.1.8.2 jruoho skip(s, tga_palette_start );
3607 1.1.8.2 jruoho // load the palette
3608 1.1.8.2 jruoho tga_palette = (unsigned char*)MALLOC( tga_palette_len * tga_palette_bits / 8 );
3609 1.1.8.2 jruoho if (!getn(s, tga_palette, tga_palette_len * tga_palette_bits / 8 ))
3610 1.1.8.2 jruoho return NULL;
3611 1.1.8.2 jruoho }
3612 1.1.8.2 jruoho // load the data
3613 1.1.8.2 jruoho trans_data[0] = trans_data[1] = trans_data[2] = trans_data[3] = 0;
3614 1.1.8.2 jruoho for (i=0; i < tga_width * tga_height; ++i)
3615 1.1.8.2 jruoho {
3616 1.1.8.2 jruoho // if I'm in RLE mode, do I need to get a RLE chunk?
3617 1.1.8.2 jruoho if ( tga_is_RLE )
3618 1.1.8.2 jruoho {
3619 1.1.8.2 jruoho if ( RLE_count == 0 )
3620 1.1.8.2 jruoho {
3621 1.1.8.2 jruoho // yep, get the next byte as a RLE command
3622 1.1.8.2 jruoho int RLE_cmd = get8u(s);
3623 1.1.8.2 jruoho RLE_count = 1 + (RLE_cmd & 127);
3624 1.1.8.2 jruoho RLE_repeating = RLE_cmd >> 7;
3625 1.1.8.2 jruoho read_next_pixel = 1;
3626 1.1.8.2 jruoho } else if ( !RLE_repeating )
3627 1.1.8.2 jruoho {
3628 1.1.8.2 jruoho read_next_pixel = 1;
3629 1.1.8.2 jruoho }
3630 1.1.8.2 jruoho } else
3631 1.1.8.2 jruoho {
3632 1.1.8.2 jruoho read_next_pixel = 1;
3633 1.1.8.2 jruoho }
3634 1.1.8.2 jruoho // OK, if I need to read a pixel, do it now
3635 1.1.8.2 jruoho if ( read_next_pixel )
3636 1.1.8.2 jruoho {
3637 1.1.8.2 jruoho // load however much data we did have
3638 1.1.8.2 jruoho if ( tga_indexed )
3639 1.1.8.2 jruoho {
3640 1.1.8.2 jruoho // read in 1 byte, then perform the lookup
3641 1.1.8.2 jruoho int pal_idx = get8u(s);
3642 1.1.8.2 jruoho if ( pal_idx >= tga_palette_len )
3643 1.1.8.2 jruoho {
3644 1.1.8.2 jruoho // invalid index
3645 1.1.8.2 jruoho pal_idx = 0;
3646 1.1.8.2 jruoho }
3647 1.1.8.2 jruoho pal_idx *= tga_bits_per_pixel / 8;
3648 1.1.8.2 jruoho for (j = 0; j*8 < tga_bits_per_pixel; ++j)
3649 1.1.8.2 jruoho {
3650 1.1.8.2 jruoho raw_data[j] = tga_palette[pal_idx+j];
3651 1.1.8.2 jruoho }
3652 1.1.8.2 jruoho } else
3653 1.1.8.2 jruoho {
3654 1.1.8.2 jruoho // read in the data raw
3655 1.1.8.2 jruoho for (j = 0; j*8 < tga_bits_per_pixel; ++j)
3656 1.1.8.2 jruoho {
3657 1.1.8.2 jruoho raw_data[j] = get8u(s);
3658 1.1.8.2 jruoho }
3659 1.1.8.2 jruoho }
3660 1.1.8.2 jruoho // convert raw to the intermediate format
3661 1.1.8.2 jruoho switch (tga_bits_per_pixel)
3662 1.1.8.2 jruoho {
3663 1.1.8.2 jruoho case 8:
3664 1.1.8.2 jruoho // Luminous => RGBA
3665 1.1.8.2 jruoho trans_data[0] = raw_data[0];
3666 1.1.8.2 jruoho trans_data[1] = raw_data[0];
3667 1.1.8.2 jruoho trans_data[2] = raw_data[0];
3668 1.1.8.2 jruoho trans_data[3] = 255;
3669 1.1.8.2 jruoho break;
3670 1.1.8.2 jruoho case 16:
3671 1.1.8.2 jruoho // Luminous,Alpha => RGBA
3672 1.1.8.2 jruoho trans_data[0] = raw_data[0];
3673 1.1.8.2 jruoho trans_data[1] = raw_data[0];
3674 1.1.8.2 jruoho trans_data[2] = raw_data[0];
3675 1.1.8.2 jruoho trans_data[3] = raw_data[1];
3676 1.1.8.2 jruoho break;
3677 1.1.8.2 jruoho case 24:
3678 1.1.8.2 jruoho // BGR => RGBA
3679 1.1.8.2 jruoho trans_data[0] = raw_data[2];
3680 1.1.8.2 jruoho trans_data[1] = raw_data[1];
3681 1.1.8.2 jruoho trans_data[2] = raw_data[0];
3682 1.1.8.2 jruoho trans_data[3] = 255;
3683 1.1.8.2 jruoho break;
3684 1.1.8.2 jruoho case 32:
3685 1.1.8.2 jruoho // BGRA => RGBA
3686 1.1.8.2 jruoho trans_data[0] = raw_data[2];
3687 1.1.8.2 jruoho trans_data[1] = raw_data[1];
3688 1.1.8.2 jruoho trans_data[2] = raw_data[0];
3689 1.1.8.2 jruoho trans_data[3] = raw_data[3];
3690 1.1.8.2 jruoho break;
3691 1.1.8.2 jruoho }
3692 1.1.8.2 jruoho // clear the reading flag for the next pixel
3693 1.1.8.2 jruoho read_next_pixel = 0;
3694 1.1.8.2 jruoho } // end of reading a pixel
3695 1.1.8.2 jruoho // convert to final format
3696 1.1.8.2 jruoho switch (req_comp)
3697 1.1.8.2 jruoho {
3698 1.1.8.2 jruoho case 1:
3699 1.1.8.2 jruoho // RGBA => Luminance
3700 1.1.8.2 jruoho tga_data[i*req_comp+0] = compute_y(trans_data[0],trans_data[1],trans_data[2]);
3701 1.1.8.2 jruoho break;
3702 1.1.8.2 jruoho case 2:
3703 1.1.8.2 jruoho // RGBA => Luminance,Alpha
3704 1.1.8.2 jruoho tga_data[i*req_comp+0] = compute_y(trans_data[0],trans_data[1],trans_data[2]);
3705 1.1.8.2 jruoho tga_data[i*req_comp+1] = trans_data[3];
3706 1.1.8.2 jruoho break;
3707 1.1.8.2 jruoho case 3:
3708 1.1.8.2 jruoho // RGBA => RGB
3709 1.1.8.2 jruoho tga_data[i*req_comp+0] = trans_data[0];
3710 1.1.8.2 jruoho tga_data[i*req_comp+1] = trans_data[1];
3711 1.1.8.2 jruoho tga_data[i*req_comp+2] = trans_data[2];
3712 1.1.8.2 jruoho break;
3713 1.1.8.2 jruoho case 4:
3714 1.1.8.2 jruoho // RGBA => RGBA
3715 1.1.8.2 jruoho tga_data[i*req_comp+0] = trans_data[0];
3716 1.1.8.2 jruoho tga_data[i*req_comp+1] = trans_data[1];
3717 1.1.8.2 jruoho tga_data[i*req_comp+2] = trans_data[2];
3718 1.1.8.2 jruoho tga_data[i*req_comp+3] = trans_data[3];
3719 1.1.8.2 jruoho break;
3720 1.1.8.2 jruoho }
3721 1.1.8.2 jruoho // in case we're in RLE mode, keep counting down
3722 1.1.8.2 jruoho --RLE_count;
3723 1.1.8.2 jruoho }
3724 1.1.8.2 jruoho // do I need to invert the image?
3725 1.1.8.2 jruoho if ( tga_inverted )
3726 1.1.8.2 jruoho {
3727 1.1.8.2 jruoho for (j = 0; j*2 < tga_height; ++j)
3728 1.1.8.2 jruoho {
3729 1.1.8.2 jruoho int index1 = j * tga_width * req_comp;
3730 1.1.8.2 jruoho int index2 = (tga_height - 1 - j) * tga_width * req_comp;
3731 1.1.8.2 jruoho for (i = tga_width * req_comp; i > 0; --i)
3732 1.1.8.2 jruoho {
3733 1.1.8.2 jruoho unsigned char temp = tga_data[index1];
3734 1.1.8.2 jruoho tga_data[index1] = tga_data[index2];
3735 1.1.8.2 jruoho tga_data[index2] = temp;
3736 1.1.8.2 jruoho ++index1;
3737 1.1.8.2 jruoho ++index2;
3738 1.1.8.2 jruoho }
3739 1.1.8.2 jruoho }
3740 1.1.8.2 jruoho }
3741 1.1.8.2 jruoho // clear my palette, if I had one
3742 1.1.8.2 jruoho if ( tga_palette != NULL )
3743 1.1.8.2 jruoho {
3744 1.1.8.2 jruoho FREE( tga_palette );
3745 1.1.8.2 jruoho }
3746 1.1.8.2 jruoho // the things I do to get rid of an error message, and yet keep
3747 1.1.8.2 jruoho // Microsoft's C compilers happy... [8^(
3748 1.1.8.2 jruoho tga_palette_start = tga_palette_len = tga_palette_bits =
3749 1.1.8.2 jruoho tga_x_origin = tga_y_origin = 0;
3750 1.1.8.2 jruoho // OK, done
3751 1.1.8.2 jruoho return tga_data;
3752 1.1.8.2 jruoho }
3753 1.1.8.2 jruoho
3754 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3755 1.1.8.2 jruoho stbi_uc *stbi_tga_load (char const *filename, int *x, int *y, int *comp, int req_comp)
3756 1.1.8.2 jruoho {
3757 1.1.8.2 jruoho stbi_uc *data;
3758 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
3759 1.1.8.2 jruoho if (!f) return NULL;
3760 1.1.8.2 jruoho data = stbi_tga_load_from_file(f, x,y,comp,req_comp);
3761 1.1.8.2 jruoho fclose(f);
3762 1.1.8.2 jruoho return data;
3763 1.1.8.2 jruoho }
3764 1.1.8.2 jruoho
3765 1.1.8.2 jruoho stbi_uc *stbi_tga_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp)
3766 1.1.8.2 jruoho {
3767 1.1.8.2 jruoho stbi s;
3768 1.1.8.2 jruoho start_file(&s, f);
3769 1.1.8.2 jruoho return tga_load(&s, x,y,comp,req_comp);
3770 1.1.8.2 jruoho }
3771 1.1.8.2 jruoho #endif
3772 1.1.8.2 jruoho
3773 1.1.8.2 jruoho stbi_uc *stbi_tga_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
3774 1.1.8.2 jruoho {
3775 1.1.8.2 jruoho stbi s;
3776 1.1.8.2 jruoho start_mem(&s, buffer, len);
3777 1.1.8.2 jruoho return tga_load(&s, x,y,comp,req_comp);
3778 1.1.8.2 jruoho }
3779 1.1.8.2 jruoho
3780 1.1.8.2 jruoho
3781 1.1.8.2 jruoho // *************************************************************************************************
3782 1.1.8.2 jruoho // Photoshop PSD loader -- PD by Thatcher Ulrich, integration by Nicolas Schulz, tweaked by STB
3783 1.1.8.2 jruoho
3784 1.1.8.2 jruoho static int psd_test(stbi *s)
3785 1.1.8.2 jruoho {
3786 1.1.8.2 jruoho if (get32(s) != 0x38425053) return 0; // "8BPS"
3787 1.1.8.2 jruoho else return 1;
3788 1.1.8.2 jruoho }
3789 1.1.8.2 jruoho
3790 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3791 1.1.8.2 jruoho int stbi_psd_test_file(FILE *f)
3792 1.1.8.2 jruoho {
3793 1.1.8.2 jruoho stbi s;
3794 1.1.8.2 jruoho int r,n = ftell(f);
3795 1.1.8.2 jruoho start_file(&s, f);
3796 1.1.8.2 jruoho r = psd_test(&s);
3797 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
3798 1.1.8.2 jruoho return r;
3799 1.1.8.2 jruoho }
3800 1.1.8.2 jruoho #endif
3801 1.1.8.2 jruoho
3802 1.1.8.2 jruoho int stbi_psd_test_memory(stbi_uc const *buffer, int len)
3803 1.1.8.2 jruoho {
3804 1.1.8.2 jruoho stbi s;
3805 1.1.8.2 jruoho start_mem(&s, buffer, len);
3806 1.1.8.2 jruoho return psd_test(&s);
3807 1.1.8.2 jruoho }
3808 1.1.8.2 jruoho
3809 1.1.8.2 jruoho static stbi_uc *psd_load(stbi *s, int *x, int *y, int *comp, int req_comp)
3810 1.1.8.2 jruoho {
3811 1.1.8.2 jruoho int pixelCount;
3812 1.1.8.2 jruoho int channelCount, compression;
3813 1.1.8.2 jruoho int channel, i, count, len;
3814 1.1.8.2 jruoho int w,h;
3815 1.1.8.2 jruoho uint8 *out;
3816 1.1.8.2 jruoho
3817 1.1.8.2 jruoho // Check identifier
3818 1.1.8.2 jruoho if (get32(s) != 0x38425053) // "8BPS"
3819 1.1.8.2 jruoho return epuc("not PSD", "Corrupt PSD image");
3820 1.1.8.2 jruoho
3821 1.1.8.2 jruoho // Check file type version.
3822 1.1.8.2 jruoho if (get16(s) != 1)
3823 1.1.8.2 jruoho return epuc("wrong version", "Unsupported version of PSD image");
3824 1.1.8.2 jruoho
3825 1.1.8.2 jruoho // Skip 6 reserved bytes.
3826 1.1.8.2 jruoho skip(s, 6 );
3827 1.1.8.2 jruoho
3828 1.1.8.2 jruoho // Read the number of channels (R, G, B, A, etc).
3829 1.1.8.2 jruoho channelCount = get16(s);
3830 1.1.8.2 jruoho if (channelCount < 0 || channelCount > 16)
3831 1.1.8.2 jruoho return epuc("wrong channel count", "Unsupported number of channels in PSD image");
3832 1.1.8.2 jruoho
3833 1.1.8.2 jruoho // Read the rows and columns of the image.
3834 1.1.8.2 jruoho h = get32(s);
3835 1.1.8.2 jruoho w = get32(s);
3836 1.1.8.2 jruoho
3837 1.1.8.2 jruoho // Make sure the depth is 8 bits.
3838 1.1.8.2 jruoho if (get16(s) != 8)
3839 1.1.8.2 jruoho return epuc("unsupported bit depth", "PSD bit depth is not 8 bit");
3840 1.1.8.2 jruoho
3841 1.1.8.2 jruoho // Make sure the color mode is RGB.
3842 1.1.8.2 jruoho // Valid options are:
3843 1.1.8.2 jruoho // 0: Bitmap
3844 1.1.8.2 jruoho // 1: Grayscale
3845 1.1.8.2 jruoho // 2: Indexed color
3846 1.1.8.2 jruoho // 3: RGB color
3847 1.1.8.2 jruoho // 4: CMYK color
3848 1.1.8.2 jruoho // 7: Multichannel
3849 1.1.8.2 jruoho // 8: Duotone
3850 1.1.8.2 jruoho // 9: Lab color
3851 1.1.8.2 jruoho if (get16(s) != 3)
3852 1.1.8.2 jruoho return epuc("wrong color format", "PSD is not in RGB color format");
3853 1.1.8.2 jruoho
3854 1.1.8.2 jruoho // Skip the Mode Data. (It's the palette for indexed color; other info for other modes.)
3855 1.1.8.2 jruoho skip(s,get32(s) );
3856 1.1.8.2 jruoho
3857 1.1.8.2 jruoho // Skip the image resources. (resolution, pen tool paths, etc)
3858 1.1.8.2 jruoho skip(s, get32(s) );
3859 1.1.8.2 jruoho
3860 1.1.8.2 jruoho // Skip the reserved data.
3861 1.1.8.2 jruoho skip(s, get32(s) );
3862 1.1.8.2 jruoho
3863 1.1.8.2 jruoho // Find out if the data is compressed.
3864 1.1.8.2 jruoho // Known values:
3865 1.1.8.2 jruoho // 0: no compression
3866 1.1.8.2 jruoho // 1: RLE compressed
3867 1.1.8.2 jruoho compression = get16(s);
3868 1.1.8.2 jruoho if (compression > 1)
3869 1.1.8.2 jruoho return epuc("bad compression", "PSD has an unknown compression format");
3870 1.1.8.2 jruoho
3871 1.1.8.2 jruoho // Create the destination image.
3872 1.1.8.2 jruoho out = (stbi_uc *) MALLOC(4 * w*h);
3873 1.1.8.2 jruoho if (!out) return epuc("outofmem", "Out of memory");
3874 1.1.8.2 jruoho pixelCount = w*h;
3875 1.1.8.2 jruoho
3876 1.1.8.2 jruoho // Initialize the data to zero.
3877 1.1.8.2 jruoho //memset( out, 0, pixelCount * 4 );
3878 1.1.8.2 jruoho
3879 1.1.8.2 jruoho // Finally, the image data.
3880 1.1.8.2 jruoho if (compression) {
3881 1.1.8.2 jruoho // RLE as used by .PSD and .TIFF
3882 1.1.8.2 jruoho // Loop until you get the number of unpacked bytes you are expecting:
3883 1.1.8.2 jruoho // Read the next source byte into n.
3884 1.1.8.2 jruoho // If n is between 0 and 127 inclusive, copy the next n+1 bytes literally.
3885 1.1.8.2 jruoho // Else if n is between -127 and -1 inclusive, copy the next byte -n+1 times.
3886 1.1.8.2 jruoho // Else if n is 128, noop.
3887 1.1.8.2 jruoho // Endloop
3888 1.1.8.2 jruoho
3889 1.1.8.2 jruoho // The RLE-compressed data is preceeded by a 2-byte data count for each row in the data,
3890 1.1.8.2 jruoho // which we're going to just skip.
3891 1.1.8.2 jruoho skip(s, h * channelCount * 2 );
3892 1.1.8.2 jruoho
3893 1.1.8.2 jruoho // Read the RLE data by channel.
3894 1.1.8.2 jruoho for (channel = 0; channel < 4; channel++) {
3895 1.1.8.2 jruoho uint8 *p;
3896 1.1.8.2 jruoho
3897 1.1.8.2 jruoho p = out+channel;
3898 1.1.8.2 jruoho if (channel >= channelCount) {
3899 1.1.8.2 jruoho // Fill this channel with default data.
3900 1.1.8.2 jruoho for (i = 0; i < pixelCount; i++) *p = (channel == 3 ? 255 : 0), p += 4;
3901 1.1.8.2 jruoho } else {
3902 1.1.8.2 jruoho // Read the RLE data.
3903 1.1.8.2 jruoho count = 0;
3904 1.1.8.2 jruoho while (count < pixelCount) {
3905 1.1.8.2 jruoho len = get8(s);
3906 1.1.8.2 jruoho if (len == 128) {
3907 1.1.8.2 jruoho // No-op.
3908 1.1.8.2 jruoho } else if (len < 128) {
3909 1.1.8.2 jruoho // Copy next len+1 bytes literally.
3910 1.1.8.2 jruoho len++;
3911 1.1.8.2 jruoho count += len;
3912 1.1.8.2 jruoho while (len) {
3913 1.1.8.2 jruoho *p = get8u(s);
3914 1.1.8.2 jruoho p += 4;
3915 1.1.8.2 jruoho len--;
3916 1.1.8.2 jruoho }
3917 1.1.8.2 jruoho } else if (len > 128) {
3918 1.1.8.2 jruoho uint8 val;
3919 1.1.8.2 jruoho // Next -len+1 bytes in the dest are replicated from next source byte.
3920 1.1.8.2 jruoho // (Interpret len as a negative 8-bit int.)
3921 1.1.8.2 jruoho len ^= 0x0FF;
3922 1.1.8.2 jruoho len += 2;
3923 1.1.8.2 jruoho val = get8u(s);
3924 1.1.8.2 jruoho count += len;
3925 1.1.8.2 jruoho while (len) {
3926 1.1.8.2 jruoho *p = val;
3927 1.1.8.2 jruoho p += 4;
3928 1.1.8.2 jruoho len--;
3929 1.1.8.2 jruoho }
3930 1.1.8.2 jruoho }
3931 1.1.8.2 jruoho }
3932 1.1.8.2 jruoho }
3933 1.1.8.2 jruoho }
3934 1.1.8.2 jruoho
3935 1.1.8.2 jruoho } else {
3936 1.1.8.2 jruoho // We're at the raw image data. It's each channel in order (Red, Green, Blue, Alpha, ...)
3937 1.1.8.2 jruoho // where each channel consists of an 8-bit value for each pixel in the image.
3938 1.1.8.2 jruoho
3939 1.1.8.2 jruoho // Read the data by channel.
3940 1.1.8.2 jruoho for (channel = 0; channel < 4; channel++) {
3941 1.1.8.2 jruoho uint8 *p;
3942 1.1.8.2 jruoho
3943 1.1.8.2 jruoho p = out + channel;
3944 1.1.8.2 jruoho if (channel > channelCount) {
3945 1.1.8.2 jruoho // Fill this channel with default data.
3946 1.1.8.2 jruoho for (i = 0; i < pixelCount; i++) *p = channel == 3 ? 255 : 0, p += 4;
3947 1.1.8.2 jruoho } else {
3948 1.1.8.2 jruoho // Read the data.
3949 1.1.8.2 jruoho for (i = 0; i < pixelCount; i++)
3950 1.1.8.2 jruoho *p = get8u(s), p += 4;
3951 1.1.8.2 jruoho }
3952 1.1.8.2 jruoho }
3953 1.1.8.2 jruoho }
3954 1.1.8.2 jruoho
3955 1.1.8.2 jruoho if (req_comp && req_comp != 4) {
3956 1.1.8.2 jruoho out = convert_format(out, 4, req_comp, w, h);
3957 1.1.8.2 jruoho if (out == NULL) return out; // convert_format frees input on failure
3958 1.1.8.2 jruoho }
3959 1.1.8.2 jruoho
3960 1.1.8.2 jruoho if (comp) *comp = channelCount;
3961 1.1.8.2 jruoho *y = h;
3962 1.1.8.2 jruoho *x = w;
3963 1.1.8.2 jruoho
3964 1.1.8.2 jruoho return out;
3965 1.1.8.2 jruoho }
3966 1.1.8.2 jruoho
3967 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
3968 1.1.8.2 jruoho stbi_uc *stbi_psd_load(char const *filename, int *x, int *y, int *comp, int req_comp)
3969 1.1.8.2 jruoho {
3970 1.1.8.2 jruoho stbi_uc *data;
3971 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
3972 1.1.8.2 jruoho if (!f) return NULL;
3973 1.1.8.2 jruoho data = stbi_psd_load_from_file(f, x,y,comp,req_comp);
3974 1.1.8.2 jruoho fclose(f);
3975 1.1.8.2 jruoho return data;
3976 1.1.8.2 jruoho }
3977 1.1.8.2 jruoho
3978 1.1.8.2 jruoho stbi_uc *stbi_psd_load_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
3979 1.1.8.2 jruoho {
3980 1.1.8.2 jruoho stbi s;
3981 1.1.8.2 jruoho start_file(&s, f);
3982 1.1.8.2 jruoho return psd_load(&s, x,y,comp,req_comp);
3983 1.1.8.2 jruoho }
3984 1.1.8.2 jruoho #endif
3985 1.1.8.2 jruoho
3986 1.1.8.2 jruoho stbi_uc *stbi_psd_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
3987 1.1.8.2 jruoho {
3988 1.1.8.2 jruoho stbi s;
3989 1.1.8.2 jruoho start_mem(&s, buffer, len);
3990 1.1.8.2 jruoho return psd_load(&s, x,y,comp,req_comp);
3991 1.1.8.2 jruoho }
3992 1.1.8.2 jruoho
3993 1.1.8.2 jruoho // *************************************************************************************************
3994 1.1.8.2 jruoho // Softimage PIC loader
3995 1.1.8.2 jruoho // by Tom Seddon
3996 1.1.8.2 jruoho //
3997 1.1.8.2 jruoho // See http://softimage.wiki.softimage.com/index.php/INFO:_PIC_file_format
3998 1.1.8.2 jruoho // See http://ozviz.wasp.uwa.edu.au/~pbourke/dataformats/softimagepic/
3999 1.1.8.2 jruoho
4000 1.1.8.2 jruoho static int pic_is4(stbi *s,const char *str)
4001 1.1.8.2 jruoho {
4002 1.1.8.2 jruoho int i;
4003 1.1.8.2 jruoho for (i=0; i<4; ++i)
4004 1.1.8.2 jruoho if (get8(s) != (stbi_uc)str[i])
4005 1.1.8.2 jruoho return 0;
4006 1.1.8.2 jruoho
4007 1.1.8.2 jruoho return 1;
4008 1.1.8.2 jruoho }
4009 1.1.8.2 jruoho
4010 1.1.8.2 jruoho static int pic_test(stbi *s)
4011 1.1.8.2 jruoho {
4012 1.1.8.2 jruoho int i;
4013 1.1.8.2 jruoho
4014 1.1.8.2 jruoho if (!pic_is4(s,"\x53\x80\xF6\x34"))
4015 1.1.8.2 jruoho return 0;
4016 1.1.8.2 jruoho
4017 1.1.8.2 jruoho for(i=0;i<84;++i)
4018 1.1.8.2 jruoho get8(s);
4019 1.1.8.2 jruoho
4020 1.1.8.2 jruoho if (!pic_is4(s,"PICT"))
4021 1.1.8.2 jruoho return 0;
4022 1.1.8.2 jruoho
4023 1.1.8.2 jruoho return 1;
4024 1.1.8.2 jruoho }
4025 1.1.8.2 jruoho
4026 1.1.8.2 jruoho typedef struct
4027 1.1.8.2 jruoho {
4028 1.1.8.2 jruoho stbi_uc size,type,channel;
4029 1.1.8.2 jruoho } pic_packet_t;
4030 1.1.8.2 jruoho
4031 1.1.8.2 jruoho static stbi_uc *pic_readval(stbi *s, int channel, stbi_uc *dest)
4032 1.1.8.2 jruoho {
4033 1.1.8.2 jruoho int mask=0x80, i;
4034 1.1.8.2 jruoho
4035 1.1.8.2 jruoho for (i=0; i<4; ++i, mask>>=1) {
4036 1.1.8.2 jruoho if (channel & mask) {
4037 1.1.8.2 jruoho if (at_eof(s)) return epuc("bad file","PIC file too short");
4038 1.1.8.2 jruoho dest[i]=get8u(s);
4039 1.1.8.2 jruoho }
4040 1.1.8.2 jruoho }
4041 1.1.8.2 jruoho
4042 1.1.8.2 jruoho return dest;
4043 1.1.8.2 jruoho }
4044 1.1.8.2 jruoho
4045 1.1.8.2 jruoho static void pic_copyval(int channel,stbi_uc *dest,const stbi_uc *src)
4046 1.1.8.2 jruoho {
4047 1.1.8.2 jruoho int mask=0x80,i;
4048 1.1.8.2 jruoho
4049 1.1.8.2 jruoho for (i=0;i<4; ++i, mask>>=1)
4050 1.1.8.2 jruoho if (channel&mask)
4051 1.1.8.2 jruoho dest[i]=src[i];
4052 1.1.8.2 jruoho }
4053 1.1.8.2 jruoho
4054 1.1.8.2 jruoho static stbi_uc *pic_load2(stbi *s,int width,int height,int *comp, stbi_uc *result)
4055 1.1.8.2 jruoho {
4056 1.1.8.2 jruoho int act_comp=0,num_packets=0,y,chained;
4057 1.1.8.2 jruoho pic_packet_t packets[10];
4058 1.1.8.2 jruoho
4059 1.1.8.2 jruoho // this will (should...) cater for even some bizarre stuff like having data
4060 1.1.8.2 jruoho // for the same channel in multiple packets.
4061 1.1.8.2 jruoho do {
4062 1.1.8.2 jruoho pic_packet_t *packet;
4063 1.1.8.2 jruoho
4064 1.1.8.2 jruoho if (num_packets==sizeof(packets)/sizeof(packets[0]))
4065 1.1.8.2 jruoho return epuc("bad format","too many packets");
4066 1.1.8.2 jruoho
4067 1.1.8.2 jruoho packet = &packets[num_packets++];
4068 1.1.8.2 jruoho
4069 1.1.8.2 jruoho chained = get8(s);
4070 1.1.8.2 jruoho packet->size = get8u(s);
4071 1.1.8.2 jruoho packet->type = get8u(s);
4072 1.1.8.2 jruoho packet->channel = get8u(s);
4073 1.1.8.2 jruoho
4074 1.1.8.2 jruoho act_comp |= packet->channel;
4075 1.1.8.2 jruoho
4076 1.1.8.2 jruoho if (at_eof(s)) return epuc("bad file","file too short (reading packets)");
4077 1.1.8.2 jruoho if (packet->size != 8) return epuc("bad format","packet isn't 8bpp");
4078 1.1.8.2 jruoho } while (chained);
4079 1.1.8.2 jruoho
4080 1.1.8.2 jruoho *comp = (act_comp & 0x10 ? 4 : 3); // has alpha channel?
4081 1.1.8.2 jruoho
4082 1.1.8.2 jruoho for(y=0; y<height; ++y) {
4083 1.1.8.2 jruoho int packet_idx;
4084 1.1.8.2 jruoho
4085 1.1.8.2 jruoho for(packet_idx=0; packet_idx < num_packets; ++packet_idx) {
4086 1.1.8.2 jruoho pic_packet_t *packet = &packets[packet_idx];
4087 1.1.8.2 jruoho stbi_uc *dest = result+y*width*4;
4088 1.1.8.2 jruoho
4089 1.1.8.2 jruoho switch (packet->type) {
4090 1.1.8.2 jruoho default:
4091 1.1.8.2 jruoho return epuc("bad format","packet has bad compression type");
4092 1.1.8.2 jruoho
4093 1.1.8.2 jruoho case 0: {//uncompressed
4094 1.1.8.2 jruoho int x;
4095 1.1.8.2 jruoho
4096 1.1.8.2 jruoho for(x=0;x<width;++x, dest+=4)
4097 1.1.8.2 jruoho if (!pic_readval(s,packet->channel,dest))
4098 1.1.8.2 jruoho return 0;
4099 1.1.8.2 jruoho break;
4100 1.1.8.2 jruoho }
4101 1.1.8.2 jruoho
4102 1.1.8.2 jruoho case 1://Pure RLE
4103 1.1.8.2 jruoho {
4104 1.1.8.2 jruoho int left=width, i;
4105 1.1.8.2 jruoho
4106 1.1.8.2 jruoho while (left>0) {
4107 1.1.8.2 jruoho stbi_uc count,value[4];
4108 1.1.8.2 jruoho
4109 1.1.8.2 jruoho count=get8u(s);
4110 1.1.8.2 jruoho if (at_eof(s)) return epuc("bad file","file too short (pure read count)");
4111 1.1.8.2 jruoho
4112 1.1.8.2 jruoho if (count > left)
4113 1.1.8.2 jruoho count = (uint8) left;
4114 1.1.8.2 jruoho
4115 1.1.8.2 jruoho if (!pic_readval(s,packet->channel,value)) return 0;
4116 1.1.8.2 jruoho
4117 1.1.8.2 jruoho for(i=0; i<count; ++i,dest+=4)
4118 1.1.8.2 jruoho pic_copyval(packet->channel,dest,value);
4119 1.1.8.2 jruoho left -= count;
4120 1.1.8.2 jruoho }
4121 1.1.8.2 jruoho }
4122 1.1.8.2 jruoho break;
4123 1.1.8.2 jruoho
4124 1.1.8.2 jruoho case 2: {//Mixed RLE
4125 1.1.8.2 jruoho int left=width;
4126 1.1.8.2 jruoho while (left>0) {
4127 1.1.8.2 jruoho int count = get8(s), i;
4128 1.1.8.2 jruoho if (at_eof(s)) return epuc("bad file","file too short (mixed read count)");
4129 1.1.8.2 jruoho
4130 1.1.8.2 jruoho if (count >= 128) { // Repeated
4131 1.1.8.2 jruoho stbi_uc value[4];
4132 1.1.8.2 jruoho
4133 1.1.8.2 jruoho if (count==128)
4134 1.1.8.2 jruoho count = get16(s);
4135 1.1.8.2 jruoho else
4136 1.1.8.2 jruoho count -= 127;
4137 1.1.8.2 jruoho if (count > left)
4138 1.1.8.2 jruoho return epuc("bad file","scanline overrun");
4139 1.1.8.2 jruoho
4140 1.1.8.2 jruoho if (!pic_readval(s,packet->channel,value))
4141 1.1.8.2 jruoho return 0;
4142 1.1.8.2 jruoho
4143 1.1.8.2 jruoho for(i=0;i<count;++i, dest += 4)
4144 1.1.8.2 jruoho pic_copyval(packet->channel,dest,value);
4145 1.1.8.2 jruoho } else { // Raw
4146 1.1.8.2 jruoho ++count;
4147 1.1.8.2 jruoho if (count>left) return epuc("bad file","scanline overrun");
4148 1.1.8.2 jruoho
4149 1.1.8.2 jruoho for(i=0;i<count;++i, dest+=4)
4150 1.1.8.2 jruoho if (!pic_readval(s,packet->channel,dest))
4151 1.1.8.2 jruoho return 0;
4152 1.1.8.2 jruoho }
4153 1.1.8.2 jruoho left-=count;
4154 1.1.8.2 jruoho }
4155 1.1.8.2 jruoho break;
4156 1.1.8.2 jruoho }
4157 1.1.8.2 jruoho }
4158 1.1.8.2 jruoho }
4159 1.1.8.2 jruoho }
4160 1.1.8.2 jruoho
4161 1.1.8.2 jruoho return result;
4162 1.1.8.2 jruoho }
4163 1.1.8.2 jruoho
4164 1.1.8.2 jruoho static stbi_uc *pic_load(stbi *s,int *px,int *py,int *comp,int req_comp)
4165 1.1.8.2 jruoho {
4166 1.1.8.2 jruoho stbi_uc *result;
4167 1.1.8.2 jruoho int i, x,y;
4168 1.1.8.2 jruoho
4169 1.1.8.2 jruoho for (i=0; i<92; ++i)
4170 1.1.8.2 jruoho get8(s);
4171 1.1.8.2 jruoho
4172 1.1.8.2 jruoho x = get16(s);
4173 1.1.8.2 jruoho y = get16(s);
4174 1.1.8.2 jruoho if (at_eof(s)) return epuc("bad file","file too short (pic header)");
4175 1.1.8.2 jruoho if ((1 << 28) / x < y) return epuc("too large", "Image too large to decode");
4176 1.1.8.2 jruoho
4177 1.1.8.2 jruoho get32(s); //skip `ratio'
4178 1.1.8.2 jruoho get16(s); //skip `fields'
4179 1.1.8.2 jruoho get16(s); //skip `pad'
4180 1.1.8.2 jruoho
4181 1.1.8.2 jruoho // intermediate buffer is RGBA
4182 1.1.8.2 jruoho result = (stbi_uc *) MALLOC(x*y*4);
4183 1.1.8.2 jruoho memset(result, 0xff, x*y*4);
4184 1.1.8.2 jruoho
4185 1.1.8.2 jruoho if (!pic_load2(s,x,y,comp, result)) {
4186 1.1.8.2 jruoho FREE(result);
4187 1.1.8.2 jruoho result=0;
4188 1.1.8.2 jruoho }
4189 1.1.8.2 jruoho *px = x;
4190 1.1.8.2 jruoho *py = y;
4191 1.1.8.2 jruoho if (req_comp == 0) req_comp = *comp;
4192 1.1.8.2 jruoho result=convert_format(result,4,req_comp,x,y);
4193 1.1.8.2 jruoho
4194 1.1.8.2 jruoho return result;
4195 1.1.8.2 jruoho }
4196 1.1.8.2 jruoho
4197 1.1.8.2 jruoho int stbi_pic_test_memory(stbi_uc const *buffer, int len)
4198 1.1.8.2 jruoho {
4199 1.1.8.2 jruoho stbi s;
4200 1.1.8.2 jruoho start_mem(&s,buffer,len);
4201 1.1.8.2 jruoho return pic_test(&s);
4202 1.1.8.2 jruoho }
4203 1.1.8.2 jruoho
4204 1.1.8.2 jruoho stbi_uc *stbi_pic_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
4205 1.1.8.2 jruoho {
4206 1.1.8.2 jruoho stbi s;
4207 1.1.8.2 jruoho start_mem(&s,buffer,len);
4208 1.1.8.2 jruoho return pic_load(&s,x,y,comp,req_comp);
4209 1.1.8.2 jruoho }
4210 1.1.8.2 jruoho
4211 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4212 1.1.8.2 jruoho int stbi_pic_test_file(FILE *f)
4213 1.1.8.2 jruoho {
4214 1.1.8.2 jruoho int result;
4215 1.1.8.2 jruoho long l = ftell(f);
4216 1.1.8.2 jruoho stbi s;
4217 1.1.8.2 jruoho start_file(&s,f);
4218 1.1.8.2 jruoho result = pic_test(&s);
4219 1.1.8.2 jruoho fseek(f,l,SEEK_SET);
4220 1.1.8.2 jruoho return result;
4221 1.1.8.2 jruoho }
4222 1.1.8.2 jruoho
4223 1.1.8.2 jruoho stbi_uc *stbi_pic_load(char const *filename,int *x, int *y, int *comp, int req_comp)
4224 1.1.8.2 jruoho {
4225 1.1.8.2 jruoho stbi_uc *result;
4226 1.1.8.2 jruoho FILE *f=fopen(filename,"rb");
4227 1.1.8.2 jruoho if (!f) return 0;
4228 1.1.8.2 jruoho result = stbi_pic_load_from_file(f,x,y,comp,req_comp);
4229 1.1.8.2 jruoho fclose(f);
4230 1.1.8.2 jruoho return result;
4231 1.1.8.2 jruoho }
4232 1.1.8.2 jruoho
4233 1.1.8.2 jruoho stbi_uc *stbi_pic_load_from_file(FILE *f,int *x, int *y, int *comp, int req_comp)
4234 1.1.8.2 jruoho {
4235 1.1.8.2 jruoho stbi s;
4236 1.1.8.2 jruoho start_file(&s,f);
4237 1.1.8.2 jruoho return pic_load(&s,x,y,comp,req_comp);
4238 1.1.8.2 jruoho }
4239 1.1.8.2 jruoho #endif
4240 1.1.8.2 jruoho
4241 1.1.8.2 jruoho // *************************************************************************************************
4242 1.1.8.2 jruoho // GIF loader -- public domain by Jean-Marc Lienher -- simplified/shrunk by stb
4243 1.1.8.2 jruoho typedef struct stbi_gif_lzw_struct {
4244 1.1.8.2 jruoho int16 prefix;
4245 1.1.8.2 jruoho uint8 first;
4246 1.1.8.2 jruoho uint8 suffix;
4247 1.1.8.2 jruoho } stbi_gif_lzw;
4248 1.1.8.2 jruoho
4249 1.1.8.2 jruoho typedef struct stbi_gif_struct
4250 1.1.8.2 jruoho {
4251 1.1.8.2 jruoho int w,h;
4252 1.1.8.2 jruoho stbi_uc *out; // output buffer (always 4 components)
4253 1.1.8.2 jruoho int flags, bgindex, ratio, transparent, eflags;
4254 1.1.8.2 jruoho uint8 pal[256][4];
4255 1.1.8.2 jruoho uint8 lpal[256][4];
4256 1.1.8.2 jruoho stbi_gif_lzw codes[4096];
4257 1.1.8.2 jruoho uint8 *color_table;
4258 1.1.8.2 jruoho int parse, step;
4259 1.1.8.2 jruoho int lflags;
4260 1.1.8.2 jruoho int start_x, start_y;
4261 1.1.8.2 jruoho int max_x, max_y;
4262 1.1.8.2 jruoho int cur_x, cur_y;
4263 1.1.8.2 jruoho int line_size;
4264 1.1.8.2 jruoho } stbi_gif;
4265 1.1.8.2 jruoho
4266 1.1.8.2 jruoho static int gif_test(stbi *s)
4267 1.1.8.2 jruoho {
4268 1.1.8.2 jruoho int sz;
4269 1.1.8.2 jruoho if (get8(s) != 'G' || get8(s) != 'I' || get8(s) != 'F' || get8(s) != '8') return 0;
4270 1.1.8.2 jruoho sz = get8(s);
4271 1.1.8.2 jruoho if (sz != '9' && sz != '7') return 0;
4272 1.1.8.2 jruoho if (get8(s) != 'a') return 0;
4273 1.1.8.2 jruoho return 1;
4274 1.1.8.2 jruoho }
4275 1.1.8.2 jruoho
4276 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4277 1.1.8.2 jruoho int stbi_gif_test_file (FILE *f)
4278 1.1.8.2 jruoho {
4279 1.1.8.2 jruoho stbi s;
4280 1.1.8.2 jruoho int r,n = ftell(f);
4281 1.1.8.2 jruoho start_file(&s,f);
4282 1.1.8.2 jruoho r = gif_test(&s);
4283 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
4284 1.1.8.2 jruoho return r;
4285 1.1.8.2 jruoho }
4286 1.1.8.2 jruoho #endif
4287 1.1.8.2 jruoho
4288 1.1.8.2 jruoho int stbi_gif_test_memory (stbi_uc const *buffer, int len)
4289 1.1.8.2 jruoho {
4290 1.1.8.2 jruoho stbi s;
4291 1.1.8.2 jruoho start_mem(&s, buffer, len);
4292 1.1.8.2 jruoho return gif_test(&s);
4293 1.1.8.2 jruoho }
4294 1.1.8.2 jruoho
4295 1.1.8.2 jruoho static void stbi_gif_parse_colortable(stbi *s, uint8 pal[256][4], int num_entries, int transp)
4296 1.1.8.2 jruoho {
4297 1.1.8.2 jruoho int i;
4298 1.1.8.2 jruoho for (i=0; i < num_entries; ++i) {
4299 1.1.8.2 jruoho pal[i][2] = get8u(s);
4300 1.1.8.2 jruoho pal[i][1] = get8u(s);
4301 1.1.8.2 jruoho pal[i][0] = get8u(s);
4302 1.1.8.2 jruoho pal[i][3] = transp ? 0 : 255;
4303 1.1.8.2 jruoho }
4304 1.1.8.2 jruoho }
4305 1.1.8.2 jruoho
4306 1.1.8.2 jruoho static int stbi_gif_header(stbi *s, stbi_gif *g, int *comp, int is_info)
4307 1.1.8.2 jruoho {
4308 1.1.8.2 jruoho uint8 ver;
4309 1.1.8.2 jruoho if (get8(s) != 'G' || get8(s) != 'I' || get8(s) != 'F' || get8(s) != '8')
4310 1.1.8.2 jruoho return e("not GIF", "Corrupt GIF");
4311 1.1.8.2 jruoho
4312 1.1.8.2 jruoho ver = get8u(s);
4313 1.1.8.2 jruoho if (ver != '7' && ver != '9') return e("not GIF", "Corrupt GIF");
4314 1.1.8.2 jruoho if (get8(s) != 'a') return e("not GIF", "Corrupt GIF");
4315 1.1.8.2 jruoho
4316 1.1.8.2 jruoho failure_reason = "";
4317 1.1.8.2 jruoho g->w = get16le(s);
4318 1.1.8.2 jruoho g->h = get16le(s);
4319 1.1.8.2 jruoho g->flags = get8(s);
4320 1.1.8.2 jruoho g->bgindex = get8(s);
4321 1.1.8.2 jruoho g->ratio = get8(s);
4322 1.1.8.2 jruoho g->transparent = -1;
4323 1.1.8.2 jruoho
4324 1.1.8.2 jruoho if (comp != 0) *comp = 4; // can't actually tell whether it's 3 or 4 until we parse the comments
4325 1.1.8.2 jruoho
4326 1.1.8.2 jruoho if (is_info) return 1;
4327 1.1.8.2 jruoho
4328 1.1.8.2 jruoho if (g->flags & 0x80)
4329 1.1.8.2 jruoho stbi_gif_parse_colortable(s,g->pal, 2 << (g->flags & 7), -1);
4330 1.1.8.2 jruoho
4331 1.1.8.2 jruoho return 1;
4332 1.1.8.2 jruoho }
4333 1.1.8.2 jruoho
4334 1.1.8.2 jruoho static int stbi_gif_info_raw(stbi *s, int *x, int *y, int *comp)
4335 1.1.8.2 jruoho {
4336 1.1.8.2 jruoho stbi_gif g;
4337 1.1.8.2 jruoho if (!stbi_gif_header(s, &g, comp, 1)) return 0;
4338 1.1.8.2 jruoho if (x) *x = g.w;
4339 1.1.8.2 jruoho if (y) *y = g.h;
4340 1.1.8.2 jruoho return 1;
4341 1.1.8.2 jruoho }
4342 1.1.8.2 jruoho
4343 1.1.8.2 jruoho static void stbi_out_gif_code(stbi_gif *g, uint16 code)
4344 1.1.8.2 jruoho {
4345 1.1.8.2 jruoho uint8 *p, *c;
4346 1.1.8.2 jruoho
4347 1.1.8.2 jruoho // recurse to decode the prefixes, since the linked-list is backwards,
4348 1.1.8.2 jruoho // and working backwards through an interleaved image would be nasty
4349 1.1.8.2 jruoho if (g->codes[code].prefix >= 0)
4350 1.1.8.2 jruoho stbi_out_gif_code(g, g->codes[code].prefix);
4351 1.1.8.2 jruoho
4352 1.1.8.2 jruoho if (g->cur_y >= g->max_y) return;
4353 1.1.8.2 jruoho
4354 1.1.8.2 jruoho p = &g->out[g->cur_x + g->cur_y];
4355 1.1.8.2 jruoho c = &g->color_table[g->codes[code].suffix * 4];
4356 1.1.8.2 jruoho
4357 1.1.8.2 jruoho if (c[3] >= 128) {
4358 1.1.8.2 jruoho p[0] = c[2];
4359 1.1.8.2 jruoho p[1] = c[1];
4360 1.1.8.2 jruoho p[2] = c[0];
4361 1.1.8.2 jruoho p[3] = c[3];
4362 1.1.8.2 jruoho }
4363 1.1.8.2 jruoho g->cur_x += 4;
4364 1.1.8.2 jruoho
4365 1.1.8.2 jruoho if (g->cur_x >= g->max_x) {
4366 1.1.8.2 jruoho g->cur_x = g->start_x;
4367 1.1.8.2 jruoho g->cur_y += g->step;
4368 1.1.8.2 jruoho
4369 1.1.8.2 jruoho while (g->cur_y >= g->max_y && g->parse > 0) {
4370 1.1.8.2 jruoho g->step = (1 << g->parse) * g->line_size;
4371 1.1.8.2 jruoho g->cur_y = g->start_y + (g->step >> 1);
4372 1.1.8.2 jruoho --g->parse;
4373 1.1.8.2 jruoho }
4374 1.1.8.2 jruoho }
4375 1.1.8.2 jruoho }
4376 1.1.8.2 jruoho
4377 1.1.8.2 jruoho static uint8 *stbi_process_gif_raster(stbi *s, stbi_gif *g)
4378 1.1.8.2 jruoho {
4379 1.1.8.2 jruoho uint8 lzw_cs;
4380 1.1.8.2 jruoho int32 len, code;
4381 1.1.8.2 jruoho uint32 first;
4382 1.1.8.2 jruoho int32 codesize, codemask, avail, oldcode, bits, valid_bits, clear;
4383 1.1.8.2 jruoho stbi_gif_lzw *p;
4384 1.1.8.2 jruoho
4385 1.1.8.2 jruoho lzw_cs = get8u(s);
4386 1.1.8.2 jruoho clear = 1 << lzw_cs;
4387 1.1.8.2 jruoho first = 1;
4388 1.1.8.2 jruoho codesize = lzw_cs + 1;
4389 1.1.8.2 jruoho codemask = (1 << codesize) - 1;
4390 1.1.8.2 jruoho bits = 0;
4391 1.1.8.2 jruoho valid_bits = 0;
4392 1.1.8.2 jruoho for (code = 0; code < clear; code++) {
4393 1.1.8.2 jruoho g->codes[code].prefix = -1;
4394 1.1.8.2 jruoho g->codes[code].first = (uint8) code;
4395 1.1.8.2 jruoho g->codes[code].suffix = (uint8) code;
4396 1.1.8.2 jruoho }
4397 1.1.8.2 jruoho
4398 1.1.8.2 jruoho // support no starting clear code
4399 1.1.8.2 jruoho avail = clear+2;
4400 1.1.8.2 jruoho oldcode = -1;
4401 1.1.8.2 jruoho
4402 1.1.8.2 jruoho len = 0;
4403 1.1.8.2 jruoho for(;;) {
4404 1.1.8.2 jruoho if (valid_bits < codesize) {
4405 1.1.8.2 jruoho if (len == 0) {
4406 1.1.8.2 jruoho len = get8(s); // start new block
4407 1.1.8.2 jruoho if (len == 0)
4408 1.1.8.2 jruoho return g->out;
4409 1.1.8.2 jruoho }
4410 1.1.8.2 jruoho --len;
4411 1.1.8.2 jruoho bits |= (int32) get8(s) << valid_bits;
4412 1.1.8.2 jruoho valid_bits += 8;
4413 1.1.8.2 jruoho } else {
4414 1.1.8.2 jruoho code = bits & codemask;
4415 1.1.8.2 jruoho bits >>= codesize;
4416 1.1.8.2 jruoho valid_bits -= codesize;
4417 1.1.8.2 jruoho // @OPTIMIZE: is there some way we can accelerate the non-clear path?
4418 1.1.8.2 jruoho if (code == clear) { // clear code
4419 1.1.8.2 jruoho codesize = lzw_cs + 1;
4420 1.1.8.2 jruoho codemask = (1 << codesize) - 1;
4421 1.1.8.2 jruoho avail = clear + 2;
4422 1.1.8.2 jruoho oldcode = -1;
4423 1.1.8.2 jruoho first = 0;
4424 1.1.8.2 jruoho } else if (code == clear + 1) { // end of stream code
4425 1.1.8.2 jruoho skip(s, len);
4426 1.1.8.2 jruoho while ((len = get8(s)) > 0)
4427 1.1.8.2 jruoho skip(s,len);
4428 1.1.8.2 jruoho return g->out;
4429 1.1.8.2 jruoho } else if (code <= avail) {
4430 1.1.8.2 jruoho if (first) return epuc("no clear code", "Corrupt GIF");
4431 1.1.8.2 jruoho
4432 1.1.8.2 jruoho if (oldcode >= 0) {
4433 1.1.8.2 jruoho p = &g->codes[avail++];
4434 1.1.8.2 jruoho if (avail > 4096) return epuc("too many codes", "Corrupt GIF");
4435 1.1.8.2 jruoho p->prefix = (int16) oldcode;
4436 1.1.8.2 jruoho p->first = g->codes[oldcode].first;
4437 1.1.8.2 jruoho p->suffix = (code == avail) ? p->first : g->codes[code].first;
4438 1.1.8.2 jruoho } else if (code == avail)
4439 1.1.8.2 jruoho return epuc("illegal code in raster", "Corrupt GIF");
4440 1.1.8.2 jruoho
4441 1.1.8.2 jruoho stbi_out_gif_code(g, (uint16) code);
4442 1.1.8.2 jruoho
4443 1.1.8.2 jruoho if ((avail & codemask) == 0 && avail <= 0x0FFF) {
4444 1.1.8.2 jruoho codesize++;
4445 1.1.8.2 jruoho codemask = (1 << codesize) - 1;
4446 1.1.8.2 jruoho }
4447 1.1.8.2 jruoho
4448 1.1.8.2 jruoho oldcode = code;
4449 1.1.8.2 jruoho } else {
4450 1.1.8.2 jruoho return epuc("illegal code in raster", "Corrupt GIF");
4451 1.1.8.2 jruoho }
4452 1.1.8.2 jruoho }
4453 1.1.8.2 jruoho }
4454 1.1.8.2 jruoho }
4455 1.1.8.2 jruoho
4456 1.1.8.2 jruoho static void stbi_fill_gif_background(stbi_gif *g)
4457 1.1.8.2 jruoho {
4458 1.1.8.2 jruoho int i;
4459 1.1.8.2 jruoho uint8 *c = g->pal[g->bgindex];
4460 1.1.8.2 jruoho // @OPTIMIZE: write a dword at a time
4461 1.1.8.2 jruoho for (i = 0; i < g->w * g->h * 4; i += 4) {
4462 1.1.8.2 jruoho uint8 *p = &g->out[i];
4463 1.1.8.2 jruoho p[0] = c[2];
4464 1.1.8.2 jruoho p[1] = c[1];
4465 1.1.8.2 jruoho p[2] = c[0];
4466 1.1.8.2 jruoho p[3] = c[3];
4467 1.1.8.2 jruoho }
4468 1.1.8.2 jruoho }
4469 1.1.8.2 jruoho
4470 1.1.8.2 jruoho // this function is designed to support animated gifs, although stb_image doesn't support it
4471 1.1.8.2 jruoho static uint8 *stbi_gif_load_next(stbi *s, stbi_gif *g, int *comp, int req_comp)
4472 1.1.8.2 jruoho {
4473 1.1.8.2 jruoho int i;
4474 1.1.8.2 jruoho uint8 *old_out = 0;
4475 1.1.8.2 jruoho
4476 1.1.8.2 jruoho if (g->out == 0) {
4477 1.1.8.2 jruoho if (!stbi_gif_header(s, g, comp,0)) return 0; // failure_reason set by stbi_gif_header
4478 1.1.8.2 jruoho g->out = (uint8 *) MALLOC(4 * g->w * g->h);
4479 1.1.8.2 jruoho if (g->out == 0) return epuc("outofmem", "Out of memory");
4480 1.1.8.2 jruoho stbi_fill_gif_background(g);
4481 1.1.8.2 jruoho } else {
4482 1.1.8.2 jruoho // animated-gif-only path
4483 1.1.8.2 jruoho if (((g->eflags & 0x1C) >> 2) == 3) {
4484 1.1.8.2 jruoho old_out = g->out;
4485 1.1.8.2 jruoho g->out = (uint8 *) MALLOC(4 * g->w * g->h);
4486 1.1.8.2 jruoho if (g->out == 0) return epuc("outofmem", "Out of memory");
4487 1.1.8.2 jruoho memcpy(g->out, old_out, g->w*g->h*4);
4488 1.1.8.2 jruoho }
4489 1.1.8.2 jruoho }
4490 1.1.8.2 jruoho
4491 1.1.8.2 jruoho for (;;) {
4492 1.1.8.2 jruoho switch (get8(s)) {
4493 1.1.8.2 jruoho case 0x2C: /* Image Descriptor */
4494 1.1.8.2 jruoho {
4495 1.1.8.2 jruoho int32 x, y, w, h;
4496 1.1.8.2 jruoho uint8 *o;
4497 1.1.8.2 jruoho
4498 1.1.8.2 jruoho x = get16le(s);
4499 1.1.8.2 jruoho y = get16le(s);
4500 1.1.8.2 jruoho w = get16le(s);
4501 1.1.8.2 jruoho h = get16le(s);
4502 1.1.8.2 jruoho if (((x + w) > (g->w)) || ((y + h) > (g->h)))
4503 1.1.8.2 jruoho return epuc("bad Image Descriptor", "Corrupt GIF");
4504 1.1.8.2 jruoho
4505 1.1.8.2 jruoho g->line_size = g->w * 4;
4506 1.1.8.2 jruoho g->start_x = x * 4;
4507 1.1.8.2 jruoho g->start_y = y * g->line_size;
4508 1.1.8.2 jruoho g->max_x = g->start_x + w * 4;
4509 1.1.8.2 jruoho g->max_y = g->start_y + h * g->line_size;
4510 1.1.8.2 jruoho g->cur_x = g->start_x;
4511 1.1.8.2 jruoho g->cur_y = g->start_y;
4512 1.1.8.2 jruoho
4513 1.1.8.2 jruoho g->lflags = get8(s);
4514 1.1.8.2 jruoho
4515 1.1.8.2 jruoho if (g->lflags & 0x40) {
4516 1.1.8.2 jruoho g->step = 8 * g->line_size; // first interlaced spacing
4517 1.1.8.2 jruoho g->parse = 3;
4518 1.1.8.2 jruoho } else {
4519 1.1.8.2 jruoho g->step = g->line_size;
4520 1.1.8.2 jruoho g->parse = 0;
4521 1.1.8.2 jruoho }
4522 1.1.8.2 jruoho
4523 1.1.8.2 jruoho if (g->lflags & 0x80) {
4524 1.1.8.2 jruoho stbi_gif_parse_colortable(s,g->lpal, 2 << (g->lflags & 7), g->eflags & 0x01 ? g->transparent : -1);
4525 1.1.8.2 jruoho g->color_table = (uint8 *) g->lpal;
4526 1.1.8.2 jruoho } else if (g->flags & 0x80) {
4527 1.1.8.2 jruoho for (i=0; i < 256; ++i) // @OPTIMIZE: reset only the previous transparent
4528 1.1.8.2 jruoho g->pal[i][3] = 255;
4529 1.1.8.2 jruoho if (g->transparent >= 0 && (g->eflags & 0x01))
4530 1.1.8.2 jruoho g->pal[g->transparent][3] = 0;
4531 1.1.8.2 jruoho g->color_table = (uint8 *) g->pal;
4532 1.1.8.2 jruoho } else
4533 1.1.8.2 jruoho return epuc("missing color table", "Corrupt GIF");
4534 1.1.8.2 jruoho
4535 1.1.8.2 jruoho o = stbi_process_gif_raster(s, g);
4536 1.1.8.2 jruoho if (o == NULL) return NULL;
4537 1.1.8.2 jruoho
4538 1.1.8.2 jruoho if (req_comp && req_comp != 4)
4539 1.1.8.2 jruoho o = convert_format(o, 4, req_comp, g->w, g->h);
4540 1.1.8.2 jruoho return o;
4541 1.1.8.2 jruoho }
4542 1.1.8.2 jruoho
4543 1.1.8.2 jruoho case 0x21: // Comment Extension.
4544 1.1.8.2 jruoho {
4545 1.1.8.2 jruoho int len;
4546 1.1.8.2 jruoho if (get8(s) == 0xF9) { // Graphic Control Extension.
4547 1.1.8.2 jruoho len = get8(s);
4548 1.1.8.2 jruoho if (len == 4) {
4549 1.1.8.2 jruoho g->eflags = get8(s);
4550 1.1.8.2 jruoho get16le(s); // delay
4551 1.1.8.2 jruoho g->transparent = get8(s);
4552 1.1.8.2 jruoho } else {
4553 1.1.8.2 jruoho skip(s, len);
4554 1.1.8.2 jruoho break;
4555 1.1.8.2 jruoho }
4556 1.1.8.2 jruoho }
4557 1.1.8.2 jruoho while ((len = get8(s)) != 0)
4558 1.1.8.2 jruoho skip(s, len);
4559 1.1.8.2 jruoho break;
4560 1.1.8.2 jruoho }
4561 1.1.8.2 jruoho
4562 1.1.8.2 jruoho case 0x3B: // gif stream termination code
4563 1.1.8.2 jruoho return (uint8 *) 1;
4564 1.1.8.2 jruoho
4565 1.1.8.2 jruoho default:
4566 1.1.8.2 jruoho return epuc("unknown code", "Corrupt GIF");
4567 1.1.8.2 jruoho }
4568 1.1.8.2 jruoho }
4569 1.1.8.2 jruoho }
4570 1.1.8.2 jruoho
4571 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4572 1.1.8.2 jruoho stbi_uc *stbi_gif_load (char const *filename, int *x, int *y, int *comp, int req_comp)
4573 1.1.8.2 jruoho {
4574 1.1.8.2 jruoho uint8 *data;
4575 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
4576 1.1.8.2 jruoho if (!f) return NULL;
4577 1.1.8.2 jruoho data = stbi_gif_load_from_file(f, x,y,comp,req_comp);
4578 1.1.8.2 jruoho fclose(f);
4579 1.1.8.2 jruoho return data;
4580 1.1.8.2 jruoho }
4581 1.1.8.2 jruoho
4582 1.1.8.2 jruoho stbi_uc *stbi_gif_load_from_file (FILE *f, int *x, int *y, int *comp, int req_comp)
4583 1.1.8.2 jruoho {
4584 1.1.8.2 jruoho uint8 *u = 0;
4585 1.1.8.2 jruoho stbi s;
4586 1.1.8.2 jruoho stbi_gif g={0};
4587 1.1.8.2 jruoho start_file(&s, f);
4588 1.1.8.2 jruoho
4589 1.1.8.2 jruoho u = stbi_gif_load_next(&s, &g, comp, req_comp);
4590 1.1.8.2 jruoho if (u == (void *) 1) u = 0; // end of animated gif marker
4591 1.1.8.2 jruoho if (u) {
4592 1.1.8.2 jruoho *x = g.w;
4593 1.1.8.2 jruoho *y = g.h;
4594 1.1.8.2 jruoho }
4595 1.1.8.2 jruoho
4596 1.1.8.2 jruoho return u;
4597 1.1.8.2 jruoho }
4598 1.1.8.2 jruoho #endif
4599 1.1.8.2 jruoho
4600 1.1.8.2 jruoho stbi_uc *stbi_gif_load_from_memory (stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
4601 1.1.8.2 jruoho {
4602 1.1.8.2 jruoho uint8 *u = 0;
4603 1.1.8.2 jruoho stbi s;
4604 1.1.8.2 jruoho stbi_gif g;
4605 1.1.8.2 jruoho
4606 1.1.8.2 jruoho memset(&g, 0, sizeof(g));
4607 1.1.8.2 jruoho start_mem(&s, buffer, len);
4608 1.1.8.2 jruoho u = stbi_gif_load_next(&s, &g, comp, req_comp);
4609 1.1.8.2 jruoho if (u == (void *) 1) u = 0; // end of animated gif marker
4610 1.1.8.2 jruoho if (u) {
4611 1.1.8.2 jruoho *x = g.w;
4612 1.1.8.2 jruoho *y = g.h;
4613 1.1.8.2 jruoho }
4614 1.1.8.2 jruoho return u;
4615 1.1.8.2 jruoho }
4616 1.1.8.2 jruoho
4617 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4618 1.1.8.2 jruoho int stbi_gif_info (char const *filename, int *x, int *y, int *comp)
4619 1.1.8.2 jruoho {
4620 1.1.8.2 jruoho int res;
4621 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
4622 1.1.8.2 jruoho if (!f) return 0;
4623 1.1.8.2 jruoho res = stbi_gif_info_from_file(f, x, y, comp);
4624 1.1.8.2 jruoho fclose(f);
4625 1.1.8.2 jruoho return res;
4626 1.1.8.2 jruoho }
4627 1.1.8.2 jruoho
4628 1.1.8.2 jruoho int stbi_gif_info_from_file(FILE *f, int *x, int *y, int *comp)
4629 1.1.8.2 jruoho {
4630 1.1.8.2 jruoho stbi s;
4631 1.1.8.2 jruoho int res;
4632 1.1.8.2 jruoho long n = ftell(f);
4633 1.1.8.2 jruoho start_file(&s, f);
4634 1.1.8.2 jruoho res = stbi_gif_info_raw(&s, x, y, comp);
4635 1.1.8.2 jruoho fseek(f, n, SEEK_SET);
4636 1.1.8.2 jruoho return res;
4637 1.1.8.2 jruoho }
4638 1.1.8.2 jruoho #endif // !STBI_NO_STDIO
4639 1.1.8.2 jruoho
4640 1.1.8.2 jruoho int stbi_gif_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp)
4641 1.1.8.2 jruoho {
4642 1.1.8.2 jruoho stbi s;
4643 1.1.8.2 jruoho start_mem(&s, buffer, len);
4644 1.1.8.2 jruoho return stbi_gif_info_raw(&s, x, y, comp);
4645 1.1.8.2 jruoho }
4646 1.1.8.2 jruoho
4647 1.1.8.2 jruoho
4648 1.1.8.2 jruoho
4649 1.1.8.2 jruoho
4650 1.1.8.2 jruoho // *************************************************************************************************
4651 1.1.8.2 jruoho // Radiance RGBE HDR loader
4652 1.1.8.2 jruoho // originally by Nicolas Schulz
4653 1.1.8.2 jruoho #ifndef STBI_NO_HDR
4654 1.1.8.2 jruoho static int hdr_test(stbi *s)
4655 1.1.8.2 jruoho {
4656 1.1.8.2 jruoho const char *signature = "#?RADIANCE\n";
4657 1.1.8.2 jruoho int i;
4658 1.1.8.2 jruoho for (i=0; signature[i]; ++i)
4659 1.1.8.2 jruoho if (get8(s) != signature[i])
4660 1.1.8.2 jruoho return 0;
4661 1.1.8.2 jruoho return 1;
4662 1.1.8.2 jruoho }
4663 1.1.8.2 jruoho
4664 1.1.8.2 jruoho int stbi_hdr_test_memory(stbi_uc const *buffer, int len)
4665 1.1.8.2 jruoho {
4666 1.1.8.2 jruoho stbi s;
4667 1.1.8.2 jruoho start_mem(&s, buffer, len);
4668 1.1.8.2 jruoho return hdr_test(&s);
4669 1.1.8.2 jruoho }
4670 1.1.8.2 jruoho
4671 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4672 1.1.8.2 jruoho int stbi_hdr_test_file(FILE *f)
4673 1.1.8.2 jruoho {
4674 1.1.8.2 jruoho stbi s;
4675 1.1.8.2 jruoho int r,n = ftell(f);
4676 1.1.8.2 jruoho start_file(&s, f);
4677 1.1.8.2 jruoho r = hdr_test(&s);
4678 1.1.8.2 jruoho fseek(f,n,SEEK_SET);
4679 1.1.8.2 jruoho return r;
4680 1.1.8.2 jruoho }
4681 1.1.8.2 jruoho #endif
4682 1.1.8.2 jruoho
4683 1.1.8.2 jruoho #define HDR_BUFLEN 1024
4684 1.1.8.2 jruoho static char *hdr_gettoken(stbi *z, char *buffer)
4685 1.1.8.2 jruoho {
4686 1.1.8.2 jruoho int len=0;
4687 1.1.8.2 jruoho char c = '\0';
4688 1.1.8.2 jruoho
4689 1.1.8.2 jruoho c = (char) get8(z);
4690 1.1.8.2 jruoho
4691 1.1.8.2 jruoho while (!at_eof(z) && c != '\n') {
4692 1.1.8.2 jruoho buffer[len++] = c;
4693 1.1.8.2 jruoho if (len == HDR_BUFLEN-1) {
4694 1.1.8.2 jruoho // flush to end of line
4695 1.1.8.2 jruoho while (!at_eof(z) && get8(z) != '\n')
4696 1.1.8.2 jruoho ;
4697 1.1.8.2 jruoho break;
4698 1.1.8.2 jruoho }
4699 1.1.8.2 jruoho c = (char) get8(z);
4700 1.1.8.2 jruoho }
4701 1.1.8.2 jruoho
4702 1.1.8.2 jruoho buffer[len] = 0;
4703 1.1.8.2 jruoho return buffer;
4704 1.1.8.2 jruoho }
4705 1.1.8.2 jruoho
4706 1.1.8.2 jruoho static void hdr_convert(float *output, stbi_uc *input, int req_comp)
4707 1.1.8.2 jruoho {
4708 1.1.8.2 jruoho if ( input[3] != 0 ) {
4709 1.1.8.2 jruoho float f1;
4710 1.1.8.2 jruoho // Exponent
4711 1.1.8.2 jruoho f1 = (float) ldexp(1.0f, input[3] - (int)(128 + 8));
4712 1.1.8.2 jruoho if (req_comp <= 2)
4713 1.1.8.2 jruoho output[0] = (input[0] + input[1] + input[2]) * f1 / 3;
4714 1.1.8.2 jruoho else {
4715 1.1.8.2 jruoho output[0] = input[0] * f1;
4716 1.1.8.2 jruoho output[1] = input[1] * f1;
4717 1.1.8.2 jruoho output[2] = input[2] * f1;
4718 1.1.8.2 jruoho }
4719 1.1.8.2 jruoho if (req_comp == 2) output[1] = 1;
4720 1.1.8.2 jruoho if (req_comp == 4) output[3] = 1;
4721 1.1.8.2 jruoho } else {
4722 1.1.8.2 jruoho switch (req_comp) {
4723 1.1.8.2 jruoho case 4: output[3] = 1; /* fallthrough */
4724 1.1.8.2 jruoho case 3: output[0] = output[1] = output[2] = 0;
4725 1.1.8.2 jruoho break;
4726 1.1.8.2 jruoho case 2: output[1] = 1; /* fallthrough */
4727 1.1.8.2 jruoho case 1: output[0] = 0;
4728 1.1.8.2 jruoho break;
4729 1.1.8.2 jruoho }
4730 1.1.8.2 jruoho }
4731 1.1.8.2 jruoho }
4732 1.1.8.2 jruoho
4733 1.1.8.2 jruoho
4734 1.1.8.2 jruoho static float *hdr_load(stbi *s, int *x, int *y, int *comp, int req_comp)
4735 1.1.8.2 jruoho {
4736 1.1.8.2 jruoho char buffer[HDR_BUFLEN];
4737 1.1.8.2 jruoho char *token;
4738 1.1.8.2 jruoho int valid = 0;
4739 1.1.8.2 jruoho int width, height;
4740 1.1.8.2 jruoho stbi_uc *scanline;
4741 1.1.8.2 jruoho float *hdr_data;
4742 1.1.8.2 jruoho int len;
4743 1.1.8.2 jruoho unsigned char count, value;
4744 1.1.8.2 jruoho int i, j, k, c1,c2, z;
4745 1.1.8.2 jruoho
4746 1.1.8.2 jruoho
4747 1.1.8.2 jruoho // Check identifier
4748 1.1.8.2 jruoho if (strcmp(hdr_gettoken(s,buffer), "#?RADIANCE") != 0)
4749 1.1.8.2 jruoho return epf("not HDR", "Corrupt HDR image");
4750 1.1.8.2 jruoho
4751 1.1.8.2 jruoho // Parse header
4752 1.1.8.2 jruoho for(;;) {
4753 1.1.8.2 jruoho token = hdr_gettoken(s,buffer);
4754 1.1.8.2 jruoho if (token[0] == 0) break;
4755 1.1.8.2 jruoho if (strcmp(token, "FORMAT=32-bit_rle_rgbe") == 0) valid = 1;
4756 1.1.8.2 jruoho }
4757 1.1.8.2 jruoho
4758 1.1.8.2 jruoho if (!valid) return epf("unsupported format", "Unsupported HDR format");
4759 1.1.8.2 jruoho
4760 1.1.8.2 jruoho // Parse width and height
4761 1.1.8.2 jruoho // can't use sscanf() if we're not using stdio!
4762 1.1.8.2 jruoho token = hdr_gettoken(s,buffer);
4763 1.1.8.2 jruoho if (strncmp(token, "-Y ", 3)) return epf("unsupported data layout", "Unsupported HDR format");
4764 1.1.8.2 jruoho token += 3;
4765 1.1.8.2 jruoho height = strtol(token, &token, 10);
4766 1.1.8.2 jruoho while (*token == ' ') ++token;
4767 1.1.8.2 jruoho if (strncmp(token, "+X ", 3)) return epf("unsupported data layout", "Unsupported HDR format");
4768 1.1.8.2 jruoho token += 3;
4769 1.1.8.2 jruoho width = strtol(token, NULL, 10);
4770 1.1.8.2 jruoho
4771 1.1.8.2 jruoho *x = width;
4772 1.1.8.2 jruoho *y = height;
4773 1.1.8.2 jruoho
4774 1.1.8.2 jruoho *comp = 3;
4775 1.1.8.2 jruoho if (req_comp == 0) req_comp = 3;
4776 1.1.8.2 jruoho
4777 1.1.8.2 jruoho // Read data
4778 1.1.8.2 jruoho hdr_data = (float *) MALLOC(height * width * req_comp * sizeof(float));
4779 1.1.8.2 jruoho
4780 1.1.8.2 jruoho // Load image data
4781 1.1.8.2 jruoho // image data is stored as some number of sca
4782 1.1.8.2 jruoho if ( width < 8 || width >= 32768) {
4783 1.1.8.2 jruoho // Read flat data
4784 1.1.8.2 jruoho for (j=0; j < height; ++j) {
4785 1.1.8.2 jruoho for (i=0; i < width; ++i) {
4786 1.1.8.2 jruoho stbi_uc rgbe[4];
4787 1.1.8.2 jruoho main_decode_loop:
4788 1.1.8.2 jruoho getn(s, rgbe, 4);
4789 1.1.8.2 jruoho hdr_convert(hdr_data + j * width * req_comp + i * req_comp, rgbe, req_comp);
4790 1.1.8.2 jruoho }
4791 1.1.8.2 jruoho }
4792 1.1.8.2 jruoho } else {
4793 1.1.8.2 jruoho // Read RLE-encoded data
4794 1.1.8.2 jruoho scanline = NULL;
4795 1.1.8.2 jruoho
4796 1.1.8.2 jruoho for (j = 0; j < height; ++j) {
4797 1.1.8.2 jruoho c1 = get8(s);
4798 1.1.8.2 jruoho c2 = get8(s);
4799 1.1.8.2 jruoho len = get8(s);
4800 1.1.8.2 jruoho if (c1 != 2 || c2 != 2 || (len & 0x80)) {
4801 1.1.8.2 jruoho // not run-length encoded, so we have to actually use THIS data as a decoded
4802 1.1.8.2 jruoho // pixel (note this can't be a valid pixel--one of RGB must be >= 128)
4803 1.1.8.2 jruoho uint8 rgbe[4];
4804 1.1.8.2 jruoho rgbe[0] = (uint8) c1;
4805 1.1.8.2 jruoho rgbe[1] = (uint8) c2;
4806 1.1.8.2 jruoho rgbe[2] = (uint8) len;
4807 1.1.8.2 jruoho rgbe[3] = (uint8) get8u(s);
4808 1.1.8.2 jruoho hdr_convert(hdr_data, rgbe, req_comp);
4809 1.1.8.2 jruoho i = 1;
4810 1.1.8.2 jruoho j = 0;
4811 1.1.8.2 jruoho FREE(scanline);
4812 1.1.8.2 jruoho goto main_decode_loop; // yes, this makes no sense
4813 1.1.8.2 jruoho }
4814 1.1.8.2 jruoho len <<= 8;
4815 1.1.8.2 jruoho len |= get8(s);
4816 1.1.8.2 jruoho if (len != width) { FREE(hdr_data); FREE(scanline); return epf("invalid decoded scanline length", "corrupt HDR"); }
4817 1.1.8.2 jruoho if (scanline == NULL) scanline = (stbi_uc *) MALLOC(width * 4);
4818 1.1.8.2 jruoho
4819 1.1.8.2 jruoho for (k = 0; k < 4; ++k) {
4820 1.1.8.2 jruoho i = 0;
4821 1.1.8.2 jruoho while (i < width) {
4822 1.1.8.2 jruoho count = get8u(s);
4823 1.1.8.2 jruoho if (count > 128) {
4824 1.1.8.2 jruoho // Run
4825 1.1.8.2 jruoho value = get8u(s);
4826 1.1.8.2 jruoho count -= 128;
4827 1.1.8.2 jruoho for (z = 0; z < count; ++z)
4828 1.1.8.2 jruoho scanline[i++ * 4 + k] = value;
4829 1.1.8.2 jruoho } else {
4830 1.1.8.2 jruoho // Dump
4831 1.1.8.2 jruoho for (z = 0; z < count; ++z)
4832 1.1.8.2 jruoho scanline[i++ * 4 + k] = get8u(s);
4833 1.1.8.2 jruoho }
4834 1.1.8.2 jruoho }
4835 1.1.8.2 jruoho }
4836 1.1.8.2 jruoho for (i=0; i < width; ++i)
4837 1.1.8.2 jruoho hdr_convert(hdr_data+(j*width + i)*req_comp, scanline + i*4, req_comp);
4838 1.1.8.2 jruoho }
4839 1.1.8.2 jruoho FREE(scanline);
4840 1.1.8.2 jruoho }
4841 1.1.8.2 jruoho
4842 1.1.8.2 jruoho return hdr_data;
4843 1.1.8.2 jruoho }
4844 1.1.8.2 jruoho
4845 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4846 1.1.8.2 jruoho float *stbi_hdr_load_from_file(FILE *f, int *x, int *y, int *comp, int req_comp)
4847 1.1.8.2 jruoho {
4848 1.1.8.2 jruoho stbi s;
4849 1.1.8.2 jruoho start_file(&s,f);
4850 1.1.8.2 jruoho return hdr_load(&s,x,y,comp,req_comp);
4851 1.1.8.2 jruoho }
4852 1.1.8.2 jruoho #endif
4853 1.1.8.2 jruoho
4854 1.1.8.2 jruoho float *stbi_hdr_load_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp, int req_comp)
4855 1.1.8.2 jruoho {
4856 1.1.8.2 jruoho stbi s;
4857 1.1.8.2 jruoho start_mem(&s,buffer, len);
4858 1.1.8.2 jruoho return hdr_load(&s,x,y,comp,req_comp);
4859 1.1.8.2 jruoho }
4860 1.1.8.2 jruoho
4861 1.1.8.2 jruoho #endif // STBI_NO_HDR
4862 1.1.8.2 jruoho
4863 1.1.8.2 jruoho
4864 1.1.8.2 jruoho #ifndef STBI_NO_STDIO
4865 1.1.8.2 jruoho int stbi_info(char const *filename, int *x, int *y, int *comp)
4866 1.1.8.2 jruoho {
4867 1.1.8.2 jruoho FILE *f = fopen(filename, "rb");
4868 1.1.8.2 jruoho int result;
4869 1.1.8.2 jruoho if (!f) return e("can't fopen", "Unable to open file");
4870 1.1.8.2 jruoho result = stbi_info_from_file(f, x, y, comp);
4871 1.1.8.2 jruoho fclose(f);
4872 1.1.8.2 jruoho return result;
4873 1.1.8.2 jruoho }
4874 1.1.8.2 jruoho
4875 1.1.8.2 jruoho int stbi_info_from_file(FILE *f, int *x, int *y, int *comp)
4876 1.1.8.2 jruoho {
4877 1.1.8.2 jruoho if (stbi_jpeg_info_from_file(f, x, y, comp))
4878 1.1.8.2 jruoho return 1;
4879 1.1.8.2 jruoho if (stbi_png_info_from_file(f, x, y, comp))
4880 1.1.8.2 jruoho return 1;
4881 1.1.8.2 jruoho if (stbi_gif_info_from_file(f, x, y, comp))
4882 1.1.8.2 jruoho return 1;
4883 1.1.8.2 jruoho // @TODO: stbi_bmp_info_from_file
4884 1.1.8.2 jruoho // @TODO: stbi_psd_info_from_file
4885 1.1.8.2 jruoho #ifndef STBI_NO_HDR
4886 1.1.8.2 jruoho // @TODO: stbi_hdr_info_from_file
4887 1.1.8.2 jruoho #endif
4888 1.1.8.2 jruoho // test tga last because it's a crappy test!
4889 1.1.8.2 jruoho if (stbi_tga_info_from_file(f, x, y, comp))
4890 1.1.8.2 jruoho return 1;
4891 1.1.8.2 jruoho return e("unknown image type", "Image not of any known type, or corrupt");
4892 1.1.8.2 jruoho }
4893 1.1.8.2 jruoho #endif // !STBI_NO_STDIO
4894 1.1.8.2 jruoho
4895 1.1.8.2 jruoho int stbi_info_from_memory(stbi_uc const *buffer, int len, int *x, int *y, int *comp)
4896 1.1.8.2 jruoho {
4897 1.1.8.2 jruoho if (stbi_jpeg_info_from_memory(buffer, len, x, y, comp))
4898 1.1.8.2 jruoho return 1;
4899 1.1.8.2 jruoho if (stbi_png_info_from_memory(buffer, len, x, y, comp))
4900 1.1.8.2 jruoho return 1;
4901 1.1.8.2 jruoho if (stbi_gif_info_from_memory(buffer, len, x, y, comp))
4902 1.1.8.2 jruoho return 1;
4903 1.1.8.2 jruoho // @TODO: stbi_bmp_info_from_memory
4904 1.1.8.2 jruoho // @TODO: stbi_psd_info_from_memory
4905 1.1.8.2 jruoho #ifndef STBI_NO_HDR
4906 1.1.8.2 jruoho // @TODO: stbi_hdr_info_from_memory
4907 1.1.8.2 jruoho #endif
4908 1.1.8.2 jruoho // test tga last because it's a crappy test!
4909 1.1.8.2 jruoho if (stbi_tga_info_from_memory(buffer, len, x, y, comp))
4910 1.1.8.2 jruoho return 1;
4911 1.1.8.2 jruoho return e("unknown image type", "Image not of any known type, or corrupt");
4912 1.1.8.2 jruoho }
4913 1.1.8.2 jruoho
4914 1.1.8.2 jruoho #endif // STBI_HEADER_FILE_ONLY
4915 1.1.8.2 jruoho
4916 1.1.8.2 jruoho /*
4917 1.1.8.2 jruoho revision history:
4918 1.1.8.2 jruoho 1.29 (2010-08-16) various warning fixes from Aurelien Pocheville
4919 1.1.8.2 jruoho 1.28 (2010-08-01) fix bug in GIF palette transparency (SpartanJ)
4920 1.1.8.2 jruoho 1.27 (2010-08-01)
4921 1.1.8.2 jruoho cast-to-uint8 to fix warnings
4922 1.1.8.2 jruoho 1.26 (2010-07-24)
4923 1.1.8.2 jruoho fix bug in file buffering for PNG reported by SpartanJ
4924 1.1.8.2 jruoho 1.25 (2010-07-17)
4925 1.1.8.2 jruoho refix trans_data warning (Won Chun)
4926 1.1.8.2 jruoho 1.24 (2010-07-12)
4927 1.1.8.2 jruoho perf improvements reading from files on platforms with lock-heavy fgetc()
4928 1.1.8.2 jruoho minor perf improvements for jpeg
4929 1.1.8.2 jruoho deprecated type-specific functions so we'll get feedback if they're needed
4930 1.1.8.2 jruoho attempt to fix trans_data warning (Won Chun)
4931 1.1.8.2 jruoho 1.23 fixed bug in iPhone support
4932 1.1.8.2 jruoho 1.22 (2010-07-10)
4933 1.1.8.2 jruoho removed image *writing* support
4934 1.1.8.2 jruoho removed image *writing* support
4935 1.1.8.2 jruoho stbi_info support from Jetro Lauha
4936 1.1.8.2 jruoho GIF support from Jean-Marc Lienher
4937 1.1.8.2 jruoho iPhone PNG-extensions from James Brown
4938 1.1.8.2 jruoho warning-fixes from Nicolas Schulz and Janez Zemva (i.e. Janez (U+017D)emva)
4939 1.1.8.2 jruoho 1.21 fix use of 'uint8' in header (reported by jon blow)
4940 1.1.8.2 jruoho 1.20 added support for Softimage PIC, by Tom Seddon
4941 1.1.8.2 jruoho 1.19 bug in interlaced PNG corruption check (found by ryg)
4942 1.1.8.2 jruoho 1.18 2008-08-02
4943 1.1.8.2 jruoho fix a threading bug (local mutable static)
4944 1.1.8.2 jruoho 1.17 support interlaced PNG
4945 1.1.8.2 jruoho 1.16 major bugfix - convert_format converted one too many pixels
4946 1.1.8.2 jruoho 1.15 initialize some fields for thread safety
4947 1.1.8.2 jruoho 1.14 fix threadsafe conversion bug
4948 1.1.8.2 jruoho header-file-only version (#define STBI_HEADER_FILE_ONLY before including)
4949 1.1.8.2 jruoho 1.13 threadsafe
4950 1.1.8.2 jruoho 1.12 const qualifiers in the API
4951 1.1.8.2 jruoho 1.11 Support installable IDCT, colorspace conversion routines
4952 1.1.8.2 jruoho 1.10 Fixes for 64-bit (don't use "unsigned long")
4953 1.1.8.2 jruoho optimized upsampling by Fabian "ryg" Giesen
4954 1.1.8.2 jruoho 1.09 Fix format-conversion for PSD code (bad global variables!)
4955 1.1.8.2 jruoho 1.08 Thatcher Ulrich's PSD code integrated by Nicolas Schulz
4956 1.1.8.2 jruoho 1.07 attempt to fix C++ warning/errors again
4957 1.1.8.2 jruoho 1.06 attempt to fix C++ warning/errors again
4958 1.1.8.2 jruoho 1.05 fix TGA loading to return correct *comp and use good luminance calc
4959 1.1.8.2 jruoho 1.04 default float alpha is 1, not 255; use 'void *' for stbi_image_free
4960 1.1.8.2 jruoho 1.03 bugfixes to STBI_NO_STDIO, STBI_NO_HDR
4961 1.1.8.2 jruoho 1.02 support for (subset of) HDR files, float interface for preferred access to them
4962 1.1.8.2 jruoho 1.01 fix bug: possible bug in handling right-side up bmps... not sure
4963 1.1.8.2 jruoho fix bug: the stbi_bmp_load() and stbi_tga_load() functions didn't work at all
4964 1.1.8.2 jruoho 1.00 interface to zlib that skips zlib header
4965 1.1.8.2 jruoho 0.99 correct handling of alpha in palette
4966 1.1.8.2 jruoho 0.98 TGA loader by lonesock; dynamically add loaders (untested)
4967 1.1.8.2 jruoho 0.97 jpeg errors on too large a file; also catch another malloc failure
4968 1.1.8.2 jruoho 0.96 fix detection of invalid v value - particleman@mollyrocket forum
4969 1.1.8.2 jruoho 0.95 during header scan, seek to markers in case of padding
4970 1.1.8.2 jruoho 0.94 STBI_NO_STDIO to disable stdio usage; rename all #defines the same
4971 1.1.8.2 jruoho 0.93 handle jpegtran output; verbose errors
4972 1.1.8.2 jruoho 0.92 read 4,8,16,24,32-bit BMP files of several formats
4973 1.1.8.2 jruoho 0.91 output 24-bit Windows 3.0 BMP files
4974 1.1.8.2 jruoho 0.90 fix a few more warnings; bump version number to approach 1.0
4975 1.1.8.2 jruoho 0.61 bugfixes due to Marc LeBlanc, Christopher Lloyd
4976 1.1.8.2 jruoho 0.60 fix compiling as c++
4977 1.1.8.2 jruoho 0.59 fix warnings: merge Dave Moore's -Wall fixes
4978 1.1.8.2 jruoho 0.58 fix bug: zlib uncompressed mode len/nlen was wrong endian
4979 1.1.8.2 jruoho 0.57 fix bug: jpg last huffman symbol before marker was >9 bits but less
4980 1.1.8.2 jruoho than 16 available
4981 1.1.8.2 jruoho 0.56 fix bug: zlib uncompressed mode len vs. nlen
4982 1.1.8.2 jruoho 0.55 fix bug: restart_interval not initialized to 0
4983 1.1.8.2 jruoho 0.54 allow NULL for 'int *comp'
4984 1.1.8.2 jruoho 0.53 fix bug in png 3->4; speedup png decoding
4985 1.1.8.2 jruoho 0.52 png handles req_comp=3,4 directly; minor cleanup; jpeg comments
4986 1.1.8.2 jruoho 0.51 obey req_comp requests, 1-component jpegs return as 1-component,
4987 1.1.8.2 jruoho on 'test' only check type, not whether we support this variant
4988 1.1.8.2 jruoho */
4989