blob: b5f330d734178f1c9e24f88e8b5eef0090d68af1 [file] [log] [blame]
cristy3ed852e2009-09-05 21:47:34 +00001/*
2%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3% %
4% %
5% %
6% JJJJJ BBBB IIIII GGGG %
7% J B B I G %
8% J BBBB I G GG %
9% J J B B I G G %
10% JJJ BBBB IIIII GGG %
11% %
12% %
13% Read/Write JBIG Image Format %
14% %
15% Software Design %
16% John Cristy %
17% July 1992 %
18% %
19% %
cristy45ef08f2012-12-07 13:13:34 +000020% Copyright 1999-2013 ImageMagick Studio LLC, a non-profit organization %
cristy3ed852e2009-09-05 21:47:34 +000021% dedicated to making software imaging solutions freely available. %
22% %
23% You may not use this file except in compliance with the License. You may %
24% obtain a copy of the License at %
25% %
26% http://www.imagemagick.org/script/license.php %
27% %
28% Unless required by applicable law or agreed to in writing, software %
29% distributed under the License is distributed on an "AS IS" BASIS, %
30% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
31% See the License for the specific language governing permissions and %
32% limitations under the License. %
33% %
34%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
35%
36%
37*/
38
39/*
40 Include declarations.
41*/
cristy4c08aed2011-07-01 19:47:50 +000042#include "MagickCore/studio.h"
cristy597d3d82012-06-17 18:44:49 +000043#include "MagickCore/attribute.h"
cristy4c08aed2011-07-01 19:47:50 +000044#include "MagickCore/blob.h"
45#include "MagickCore/blob-private.h"
46#include "MagickCore/cache.h"
47#include "MagickCore/color-private.h"
48#include "MagickCore/colormap.h"
49#include "MagickCore/colorspace.h"
cristyd15d8e02011-07-07 00:17:15 +000050#include "MagickCore/colorspace-private.h"
cristy4c08aed2011-07-01 19:47:50 +000051#include "MagickCore/constitute.h"
52#include "MagickCore/exception.h"
53#include "MagickCore/exception-private.h"
54#include "MagickCore/geometry.h"
55#include "MagickCore/image.h"
56#include "MagickCore/image-private.h"
57#include "MagickCore/list.h"
58#include "MagickCore/magick.h"
59#include "MagickCore/memory_.h"
60#include "MagickCore/monitor.h"
61#include "MagickCore/monitor-private.h"
cristy2c5fc272012-02-22 01:27:46 +000062#include "MagickCore/nt-base-private.h"
cristy4c08aed2011-07-01 19:47:50 +000063#include "MagickCore/pixel-accessor.h"
64#include "MagickCore/quantum-private.h"
65#include "MagickCore/static.h"
66#include "MagickCore/string_.h"
cristy196372d2011-11-05 00:07:32 +000067#include "MagickCore/string-private.h"
cristy4c08aed2011-07-01 19:47:50 +000068#include "MagickCore/module.h"
cristy3ed852e2009-09-05 21:47:34 +000069#if defined(MAGICKCORE_JBIG_DELEGATE)
70#include "jbig.h"
71#endif
72
73/*
74 Forward declarations.
75*/
76#if defined(MAGICKCORE_JBIG_DELEGATE)
77static MagickBooleanType
cristy1e178e72011-08-28 19:44:34 +000078 WriteJBIGImage(const ImageInfo *,Image *,ExceptionInfo *);
cristy3ed852e2009-09-05 21:47:34 +000079#endif
80
81#if defined(MAGICKCORE_JBIG_DELEGATE)
82/*
83%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
84% %
85% %
86% %
87% R e a d J B I G I m a g e %
88% %
89% %
90% %
91%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
92%
93% ReadJBIGImage() reads a JBIG image file and returns it. It
94% allocates the memory necessary for the new Image structure and returns a
95% pointer to the new image.
96%
97% The format of the ReadJBIGImage method is:
98%
99% Image *ReadJBIGImage(const ImageInfo *image_info,
100% ExceptionInfo *exception)
101%
102% A description of each parameter follows:
103%
104% o image_info: the image info.
105%
106% o exception: return any errors or warnings in this structure.
107%
108*/
109static Image *ReadJBIGImage(const ImageInfo *image_info,
110 ExceptionInfo *exception)
111{
112 Image
113 *image;
114
cristy50f1ebc2011-06-05 01:35:34 +0000115 MagickStatusType
cristy3ed852e2009-09-05 21:47:34 +0000116 status;
117
cristy4c08aed2011-07-01 19:47:50 +0000118 Quantum
119 index;
cristy3ed852e2009-09-05 21:47:34 +0000120
cristybb503372010-05-27 20:51:26 +0000121 register ssize_t
cristy3ed852e2009-09-05 21:47:34 +0000122 x;
123
cristy4c08aed2011-07-01 19:47:50 +0000124 register Quantum
cristy3ed852e2009-09-05 21:47:34 +0000125 *q;
126
127 register unsigned char
128 *p;
129
130 ssize_t
cristy524222d2011-04-25 00:37:06 +0000131 length,
132 y;
cristy3ed852e2009-09-05 21:47:34 +0000133
134 struct jbg_dec_state
135 jbig_info;
136
137 unsigned char
138 bit,
139 *buffer,
140 byte;
141
142 /*
143 Open image file.
144 */
145 assert(image_info != (const ImageInfo *) NULL);
146 assert(image_info->signature == MagickSignature);
147 if (image_info->debug != MagickFalse)
148 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
149 image_info->filename);
150 assert(exception != (ExceptionInfo *) NULL);
151 assert(exception->signature == MagickSignature);
cristy9950d572011-10-01 18:22:35 +0000152 image=AcquireImage(image_info,exception);
cristy3ed852e2009-09-05 21:47:34 +0000153 status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
154 if (status == MagickFalse)
155 {
156 image=DestroyImageList(image);
157 return((Image *) NULL);
158 }
159 /*
160 Initialize JBIG toolkit.
161 */
162 jbg_dec_init(&jbig_info);
cristyf6fe0a12010-05-30 00:44:47 +0000163 jbg_dec_maxsize(&jbig_info,(unsigned long) image->columns,(unsigned long)
cristy3ed852e2009-09-05 21:47:34 +0000164 image->rows);
165 image->columns=jbg_dec_getwidth(&jbig_info);
166 image->rows=jbg_dec_getheight(&jbig_info);
167 image->depth=8;
168 image->storage_class=PseudoClass;
169 image->colors=2;
170 /*
171 Read JBIG file.
172 */
173 buffer=(unsigned char *) AcquireQuantumMemory(MagickMaxBufferExtent,
174 sizeof(*buffer));
175 if (buffer == (unsigned char *) NULL)
176 ThrowReaderException(ResourceLimitError,"MemoryAllocationFailed");
177 status=JBG_EAGAIN;
178 do
179 {
cristybb503372010-05-27 20:51:26 +0000180 length=(ssize_t) ReadBlob(image,MagickMaxBufferExtent,buffer);
cristy3ed852e2009-09-05 21:47:34 +0000181 if (length == 0)
182 break;
183 p=buffer;
cristy3ed852e2009-09-05 21:47:34 +0000184 while ((length > 0) && ((status == JBG_EAGAIN) || (status == JBG_EOK)))
185 {
186 size_t
187 count;
188
189 status=jbg_dec_in(&jbig_info,p,length,&count);
190 p+=count;
cristybb503372010-05-27 20:51:26 +0000191 length-=(ssize_t) count;
cristy3ed852e2009-09-05 21:47:34 +0000192 }
193 } while ((status == JBG_EAGAIN) || (status == JBG_EOK));
194 /*
195 Create colormap.
196 */
197 image->columns=jbg_dec_getwidth(&jbig_info);
198 image->rows=jbg_dec_getheight(&jbig_info);
cristy6d5e20f2011-04-25 13:48:54 +0000199 image->compression=JBIG2Compression;
cristy018f07f2011-09-04 21:15:19 +0000200 if (AcquireImageColormap(image,2,exception) == MagickFalse)
cristy3ed852e2009-09-05 21:47:34 +0000201 {
202 buffer=(unsigned char *) RelinquishMagickMemory(buffer);
203 ThrowReaderException(ResourceLimitError,"MemoryAllocationFailed");
204 }
205 image->colormap[0].red=0;
206 image->colormap[0].green=0;
207 image->colormap[0].blue=0;
208 image->colormap[1].red=QuantumRange;
209 image->colormap[1].green=QuantumRange;
210 image->colormap[1].blue=QuantumRange;
cristy2a11bef2011-10-28 18:33:11 +0000211 image->resolution.x=300;
212 image->resolution.y=300;
cristy3ed852e2009-09-05 21:47:34 +0000213 if (image_info->ping != MagickFalse)
214 {
215 (void) CloseBlob(image);
216 return(GetFirstImageInList(image));
217 }
218 /*
219 Convert X bitmap image to pixel packets.
220 */
221 p=jbg_dec_getimage(&jbig_info,0);
cristybb503372010-05-27 20:51:26 +0000222 for (y=0; y < (ssize_t) image->rows; y++)
cristy3ed852e2009-09-05 21:47:34 +0000223 {
224 q=QueueAuthenticPixels(image,0,y,image->columns,1,exception);
cristyacd2ed22011-08-30 01:44:23 +0000225 if (q == (Quantum *) NULL)
cristy3ed852e2009-09-05 21:47:34 +0000226 break;
cristy3ed852e2009-09-05 21:47:34 +0000227 bit=0;
228 byte=0;
cristybb503372010-05-27 20:51:26 +0000229 for (x=0; x < (ssize_t) image->columns; x++)
cristy3ed852e2009-09-05 21:47:34 +0000230 {
231 if (bit == 0)
232 byte=(*p++);
233 index=(byte & 0x80) ? 0 : 1;
234 bit++;
235 byte<<=1;
236 if (bit == 8)
237 bit=0;
cristy4c08aed2011-07-01 19:47:50 +0000238 SetPixelIndex(image,index,q);
cristy803640d2011-11-17 02:11:32 +0000239 SetPixelInfoPixel(image,image->colormap+(ssize_t) index,q);
cristyed231572011-07-14 02:18:59 +0000240 q+=GetPixelChannels(image);
cristy3ed852e2009-09-05 21:47:34 +0000241 }
242 if (SyncAuthenticPixels(image,exception) == MagickFalse)
243 break;
cristycee97112010-05-28 00:44:52 +0000244 status=SetImageProgress(image,LoadImageTag,(MagickOffsetType) y,
cristy524222d2011-04-25 00:37:06 +0000245 image->rows);
cristy3ed852e2009-09-05 21:47:34 +0000246 if (status == MagickFalse)
247 break;
248 }
249 /*
250 Free scale resource.
251 */
252 jbg_dec_free(&jbig_info);
253 buffer=(unsigned char *) RelinquishMagickMemory(buffer);
254 (void) CloseBlob(image);
255 return(GetFirstImageInList(image));
256}
257#endif
258
259/*
260%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
261% %
262% %
263% %
264% R e g i s t e r J B I G I m a g e %
265% %
266% %
267% %
268%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
269%
270% RegisterJBIGImage() adds attributes for the JBIG image format to
271% the list of supported formats. The attributes include the image format
272% tag, a method to read and/or write the format, whether the format
273% supports the saving of more than one frame to the same file or blob,
274% whether the format supports native in-memory I/O, and a brief
275% description of the format.
276%
277% The format of the RegisterJBIGImage method is:
278%
cristybb503372010-05-27 20:51:26 +0000279% size_t RegisterJBIGImage(void)
cristy3ed852e2009-09-05 21:47:34 +0000280%
281*/
cristybb503372010-05-27 20:51:26 +0000282ModuleExport size_t RegisterJBIGImage(void)
cristy3ed852e2009-09-05 21:47:34 +0000283{
284#define JBIGDescription "Joint Bi-level Image experts Group interchange format"
285
286 char
287 version[MaxTextExtent];
288
289 MagickInfo
290 *entry;
291
292 *version='\0';
293#if defined(JBG_VERSION)
294 (void) CopyMagickString(version,JBG_VERSION,MaxTextExtent);
295#endif
296 entry=SetMagickInfo("BIE");
297#if defined(MAGICKCORE_JBIG_DELEGATE)
298 entry->decoder=(DecodeImageHandler *) ReadJBIGImage;
299 entry->encoder=(EncodeImageHandler *) WriteJBIGImage;
300#endif
301 entry->adjoin=MagickFalse;
302 entry->description=ConstantString(JBIGDescription);
303 if (*version != '\0')
304 entry->version=ConstantString(version);
305 entry->module=ConstantString("JBIG");
306 (void) RegisterMagickInfo(entry);
307 entry=SetMagickInfo("JBG");
308#if defined(MAGICKCORE_JBIG_DELEGATE)
309 entry->decoder=(DecodeImageHandler *) ReadJBIGImage;
310 entry->encoder=(EncodeImageHandler *) WriteJBIGImage;
311#endif
312 entry->description=ConstantString(JBIGDescription);
313 if (*version != '\0')
314 entry->version=ConstantString(version);
315 entry->module=ConstantString("JBIG");
316 (void) RegisterMagickInfo(entry);
317 entry=SetMagickInfo("JBIG");
318#if defined(MAGICKCORE_JBIG_DELEGATE)
319 entry->decoder=(DecodeImageHandler *) ReadJBIGImage;
320 entry->encoder=(EncodeImageHandler *) WriteJBIGImage;
321#endif
322 entry->description=ConstantString(JBIGDescription);
323 if (*version != '\0')
324 entry->version=ConstantString(version);
325 entry->module=ConstantString("JBIG");
326 (void) RegisterMagickInfo(entry);
327 return(MagickImageCoderSignature);
328}
329
330/*
331%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
332% %
333% %
334% %
335% U n r e g i s t e r J B I G I m a g e %
336% %
337% %
338% %
339%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
340%
341% UnregisterJBIGImage() removes format registrations made by the
342% JBIG module from the list of supported formats.
343%
344% The format of the UnregisterJBIGImage method is:
345%
346% UnregisterJBIGImage(void)
347%
348*/
349ModuleExport void UnregisterJBIGImage(void)
350{
351 (void) UnregisterMagickInfo("BIE");
352 (void) UnregisterMagickInfo("JBG");
353 (void) UnregisterMagickInfo("JBIG");
354}
355
356#if defined(MAGICKCORE_JBIG_DELEGATE)
357/*
358%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
359% %
360% %
361% %
362% W r i t e J B I G I m a g e %
363% %
364% %
365% %
366%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
367%
368% WriteJBIGImage() writes an image in the JBIG encoded image format.
369%
370% The format of the WriteJBIGImage method is:
371%
cristy1e178e72011-08-28 19:44:34 +0000372% MagickBooleanType WriteJBIGImage(const ImageInfo *image_info,
373% Image *image,ExceptionInfo *exception)
cristy3ed852e2009-09-05 21:47:34 +0000374%
375% A description of each parameter follows.
376%
377% o image_info: the image info.
378%
379% o image: The image.
380%
cristy1e178e72011-08-28 19:44:34 +0000381% o exception: return any errors or warnings in this structure.
cristy3ed852e2009-09-05 21:47:34 +0000382%
383*/
384
385static void JBIGEncode(unsigned char *pixels,size_t length,void *data)
386{
387 Image
388 *image;
389
390 image=(Image *) data;
391 (void) WriteBlob(image,length,pixels);
392}
393
394static MagickBooleanType WriteJBIGImage(const ImageInfo *image_info,
cristy1e178e72011-08-28 19:44:34 +0000395 Image *image,ExceptionInfo *exception)
cristy3ed852e2009-09-05 21:47:34 +0000396{
397 double
398 version;
399
cristy3ed852e2009-09-05 21:47:34 +0000400 MagickBooleanType
401 status;
402
403 MagickOffsetType
404 scene;
405
cristy4c08aed2011-07-01 19:47:50 +0000406 register const Quantum
cristy3ed852e2009-09-05 21:47:34 +0000407 *p;
408
cristybb503372010-05-27 20:51:26 +0000409 register ssize_t
cristy3ed852e2009-09-05 21:47:34 +0000410 x;
411
412 register unsigned char
413 *q;
414
cristy524222d2011-04-25 00:37:06 +0000415 size_t
416 number_packets;
417
418 ssize_t
419 y;
420
cristy3ed852e2009-09-05 21:47:34 +0000421 struct jbg_enc_state
422 jbig_info;
423
424 unsigned char
425 bit,
426 byte,
427 *pixels;
428
cristy3ed852e2009-09-05 21:47:34 +0000429 /*
430 Open image file.
431 */
432 assert(image_info != (const ImageInfo *) NULL);
433 assert(image_info->signature == MagickSignature);
434 assert(image != (Image *) NULL);
435 assert(image->signature == MagickSignature);
436 if (image->debug != MagickFalse)
437 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
cristy3a37efd2011-08-28 20:31:03 +0000438 assert(exception != (ExceptionInfo *) NULL);
439 assert(exception->signature == MagickSignature);
cristy1e178e72011-08-28 19:44:34 +0000440 status=OpenBlob(image_info,image,WriteBinaryBlobMode,exception);
cristy3ed852e2009-09-05 21:47:34 +0000441 if (status == MagickFalse)
442 return(status);
cristydbdd0e32011-11-04 23:29:40 +0000443 version=StringToDouble(JBG_VERSION,(char **) NULL);
cristy3ed852e2009-09-05 21:47:34 +0000444 scene=0;
445 do
446 {
447 /*
448 Allocate pixel data.
449 */
cristy3d9f5ba2012-06-26 13:37:31 +0000450 if (IssRGBCompatibleColorspace(image->colorspace) == MagickFalse)
cristy8d951092012-02-08 18:54:56 +0000451 (void) TransformImageColorspace(image,sRGBColorspace,exception);
cristy3ed852e2009-09-05 21:47:34 +0000452 number_packets=(image->columns+7)/8;
453 pixels=(unsigned char *) AcquireQuantumMemory(number_packets,
454 image->rows*sizeof(*pixels));
455 if (pixels == (unsigned char *) NULL)
456 ThrowWriterException(ResourceLimitError,"MemoryAllocationFailed");
457 /*
458 Convert pixels to a bitmap.
459 */
cristy018f07f2011-09-04 21:15:19 +0000460 (void) SetImageType(image,BilevelType,exception);
cristy3ed852e2009-09-05 21:47:34 +0000461 q=pixels;
cristybb503372010-05-27 20:51:26 +0000462 for (y=0; y < (ssize_t) image->rows; y++)
cristy3ed852e2009-09-05 21:47:34 +0000463 {
cristy1e178e72011-08-28 19:44:34 +0000464 p=GetVirtualPixels(image,0,y,image->columns,1,exception);
cristy4c08aed2011-07-01 19:47:50 +0000465 if (p == (const Quantum *) NULL)
cristy3ed852e2009-09-05 21:47:34 +0000466 break;
cristy3ed852e2009-09-05 21:47:34 +0000467 bit=0;
468 byte=0;
cristybb503372010-05-27 20:51:26 +0000469 for (x=0; x < (ssize_t) image->columns; x++)
cristy3ed852e2009-09-05 21:47:34 +0000470 {
471 byte<<=1;
cristy4c08aed2011-07-01 19:47:50 +0000472 if (GetPixelIntensity(image,p) < (QuantumRange/2.0))
cristy3ed852e2009-09-05 21:47:34 +0000473 byte|=0x01;
474 bit++;
475 if (bit == 8)
476 {
477 *q++=byte;
478 bit=0;
479 byte=0;
480 }
cristyed231572011-07-14 02:18:59 +0000481 p+=GetPixelChannels(image);
cristy3ed852e2009-09-05 21:47:34 +0000482 }
483 if (bit != 0)
484 *q++=byte << (8-bit);
485 if (image->previous == (Image *) NULL)
486 {
cristycee97112010-05-28 00:44:52 +0000487 status=SetImageProgress(image,SaveImageTag,(MagickOffsetType) y,
cristy524222d2011-04-25 00:37:06 +0000488 image->rows);
cristy3ed852e2009-09-05 21:47:34 +0000489 if (status == MagickFalse)
490 break;
491 }
492 }
493 /*
494 Initialize JBIG info structure.
495 */
cristyf6fe0a12010-05-30 00:44:47 +0000496 jbg_enc_init(&jbig_info,(unsigned long) image->columns,(unsigned long)
497 image->rows,1,&pixels,(void (*)(unsigned char *,size_t,void *))
498 JBIGEncode,image);
cristy3ed852e2009-09-05 21:47:34 +0000499 if (image_info->scene != 0)
500 jbg_enc_layers(&jbig_info,(int) image_info->scene);
501 else
502 {
cristybb503372010-05-27 20:51:26 +0000503 size_t
cristy3ed852e2009-09-05 21:47:34 +0000504 x_resolution,
505 y_resolution;
506
507 x_resolution=640;
508 y_resolution=480;
cristy3ed852e2009-09-05 21:47:34 +0000509 if (image_info->density != (char *) NULL)
510 {
511 GeometryInfo
512 geometry_info;
513
514 MagickStatusType
515 flags;
516
517 flags=ParseGeometry(image_info->density,&geometry_info);
518 x_resolution=geometry_info.rho;
519 y_resolution=geometry_info.sigma;
520 if ((flags & SigmaValue) == 0)
521 y_resolution=x_resolution;
522 }
523 if (image->units == PixelsPerCentimeterResolution)
524 {
cristybb503372010-05-27 20:51:26 +0000525 x_resolution=(size_t) (100.0*2.54*x_resolution+0.5)/100.0;
526 y_resolution=(size_t) (100.0*2.54*y_resolution+0.5)/100.0;
cristy3ed852e2009-09-05 21:47:34 +0000527 }
cristyf6fe0a12010-05-30 00:44:47 +0000528 (void) jbg_enc_lrlmax(&jbig_info,(unsigned long) x_resolution,
529 (unsigned long) y_resolution);
cristy3ed852e2009-09-05 21:47:34 +0000530 }
531 (void) jbg_enc_lrange(&jbig_info,-1,-1);
532 jbg_enc_options(&jbig_info,JBG_ILEAVE | JBG_SMID,JBG_TPDON | JBG_TPBON |
533 JBG_DPON,version < 1.6 ? -1 : 0,-1,-1);
534 /*
535 Write JBIG image.
536 */
537 jbg_enc_out(&jbig_info);
538 jbg_enc_free(&jbig_info);
539 pixels=(unsigned char *) RelinquishMagickMemory(pixels);
540 if (GetNextImageInList(image) == (Image *) NULL)
541 break;
542 image=SyncNextImageInList(image);
543 status=SetImageProgress(image,SaveImagesTag,scene++,
544 GetImageListLength(image));
545 if (status == MagickFalse)
546 break;
547 } while (image_info->adjoin != MagickFalse);
548 (void) CloseBlob(image);
549 return(MagickTrue);
550}
551#endif