]> granicus.if.org Git - imagemagick/blob - magick/stream.c
(no commit message)
[imagemagick] / magick / stream.c
1 /*
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 %                                                                             %
4 %                                                                             %
5 %                                                                             %
6 %                  SSSSS  TTTTT  RRRR   EEEEE   AAA   M   M                   %
7 %                  SS       T    R   R  E      A   A  MM MM                   %
8 %                   SSS     T    RRRR   EEE    AAAAA  M M M                   %
9 %                     SS    T    R R    E      A   A  M   M                   %
10 %                  SSSSS    T    R  R   EEEEE  A   A  M   M                   %
11 %                                                                             %
12 %                                                                             %
13 %                       MagickCore Pixel Stream Methods                       %
14 %                                                                             %
15 %                              Software Design                                %
16 %                                John Cristy                                  %
17 %                                 March 2000                                  %
18 %                                                                             %
19 %                                                                             %
20 %  Copyright 1999-2010 ImageMagick Studio LLC, a non-profit organization      %
21 %  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 \f
40 /*
41   Include declarations.
42 */
43 #include "magick/studio.h"
44 #include "magick/blob.h"
45 #include "magick/blob-private.h"
46 #include "magick/cache.h"
47 #include "magick/cache-private.h"
48 #include "magick/color-private.h"
49 #include "magick/composite-private.h"
50 #include "magick/constitute.h"
51 #include "magick/exception.h"
52 #include "magick/exception-private.h"
53 #include "magick/geometry.h"
54 #include "magick/memory_.h"
55 #include "magick/pixel.h"
56 #include "magick/quantum.h"
57 #include "magick/quantum-private.h"
58 #include "magick/semaphore.h"
59 #include "magick/stream.h"
60 #include "magick/stream-private.h"
61 #include "magick/string_.h"
62 \f
63 /*
64   Typedef declaractions.
65 */
66 struct _StreamInfo
67 {
68   const ImageInfo
69     *image_info;
70
71   const Image
72     *image;
73
74   Image
75     *stream;
76
77   QuantumInfo
78     *quantum_info;
79
80   char
81     *map;
82
83   StorageType
84     storage_type;
85
86   unsigned char
87     *pixels;
88
89   RectangleInfo
90     extract_info;
91
92   long
93     y;
94
95   ExceptionInfo
96     *exception;
97
98   const void
99     *client_data;
100
101   unsigned long
102     signature;
103 };
104 \f
105 /*
106   Declare pixel cache interfaces.
107 */
108 #if defined(__cplusplus) || defined(c_plusplus)
109 extern "C" {
110 #endif
111
112 static const PixelPacket
113   *GetVirtualPixelStream(const Image *,const VirtualPixelMethod,const long,
114     const long,const unsigned long,const unsigned long,ExceptionInfo *);
115
116 static MagickBooleanType
117   StreamImagePixels(const StreamInfo *,const Image *,ExceptionInfo *),
118   SyncAuthenticPixelsStream(Image *,ExceptionInfo *);
119
120 static PixelPacket
121   *QueueAuthenticPixelsStream(Image *,const long,const long,const unsigned long,
122     const unsigned long,ExceptionInfo *);
123
124 #if defined(__cplusplus) || defined(c_plusplus)
125 }
126 #endif
127 \f
128 /*
129 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
130 %                                                                             %
131 %                                                                             %
132 %                                                                             %
133 +   A c q u i r e S t r e a m I n f o                                         %
134 %                                                                             %
135 %                                                                             %
136 %                                                                             %
137 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
138 %
139 %  AcquireStreamInfo() allocates the StreamInfo structure.
140 %
141 %  The format of the AcquireStreamInfo method is:
142 %
143 %      StreamInfo *AcquireStreamInfo(const ImageInfo *image_info)
144 %
145 %  A description of each parameter follows:
146 %
147 %    o image_info: the image info.
148 %
149 */
150 MagickExport StreamInfo *AcquireStreamInfo(const ImageInfo *image_info)
151 {
152   StreamInfo
153     *stream_info;
154
155   stream_info=(StreamInfo *) AcquireAlignedMemory(1,sizeof(*stream_info));
156   if (stream_info == (StreamInfo *) NULL)
157     ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
158   (void) ResetMagickMemory(stream_info,0,sizeof(*stream_info));
159   stream_info->pixels=(unsigned char *) AcquireMagickMemory(
160     sizeof(*stream_info->pixels));
161   if (stream_info->pixels == (unsigned char *) NULL)
162     ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
163   stream_info->map=ConstantString("RGB");
164   stream_info->storage_type=CharPixel;
165   stream_info->stream=AcquireImage(image_info);
166   stream_info->signature=MagickSignature;
167   return(stream_info);
168 }
169 \f
170 /*
171 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
172 %                                                                             %
173 %                                                                             %
174 %                                                                             %
175 +   D e s t r o y P i x e l S t r e a m                                       %
176 %                                                                             %
177 %                                                                             %
178 %                                                                             %
179 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
180 %
181 %  DestroyPixelStream() deallocates memory associated with the pixel stream.
182 %
183 %  The format of the DestroyPixelStream() method is:
184 %
185 %      void DestroyPixelStream(Image *image)
186 %
187 %  A description of each parameter follows:
188 %
189 %    o image: the image.
190 %
191 */
192
193 static inline void RelinquishStreamPixels(CacheInfo *cache_info)
194 {
195   assert(cache_info != (CacheInfo *) NULL);
196   if (cache_info->mapped == MagickFalse)
197     (void) RelinquishMagickMemory(cache_info->pixels);
198   else
199     (void) UnmapBlob(cache_info->pixels,(size_t) cache_info->length);
200   cache_info->pixels=(PixelPacket *) NULL;
201   cache_info->indexes=(IndexPacket *) NULL;
202   cache_info->length=0;
203   cache_info->mapped=MagickFalse;
204 }
205
206 static void DestroyPixelStream(Image *image)
207 {
208   CacheInfo
209     *cache_info;
210
211   MagickBooleanType
212     destroy;
213
214   assert(image != (Image *) NULL);
215   assert(image->signature == MagickSignature);
216   if (image->debug != MagickFalse)
217     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
218   cache_info=(CacheInfo *) image->cache;
219   assert(cache_info->signature == MagickSignature);
220   destroy=MagickFalse;
221   LockSemaphoreInfo(cache_info->semaphore);
222   cache_info->reference_count--;
223   if (cache_info->reference_count == 0)
224     destroy=MagickTrue;
225   UnlockSemaphoreInfo(cache_info->semaphore);
226   if (destroy == MagickFalse)
227     return;
228   RelinquishStreamPixels(cache_info);
229   if (cache_info->nexus_info != (NexusInfo **) NULL)
230     cache_info->nexus_info=DestroyPixelCacheNexus(cache_info->nexus_info,
231       cache_info->number_threads);
232   if (cache_info->disk_semaphore != (SemaphoreInfo *) NULL)
233     DestroySemaphoreInfo(&cache_info->disk_semaphore);
234   if (cache_info->semaphore != (SemaphoreInfo *) NULL)
235     DestroySemaphoreInfo(&cache_info->semaphore);
236   cache_info=(CacheInfo *) RelinquishMagickMemory(cache_info);
237 }
238 \f
239 /*
240 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
241 %                                                                             %
242 %                                                                             %
243 %                                                                             %
244 +   D e s t r o y S t r e a m I n f o                                         %
245 %                                                                             %
246 %                                                                             %
247 %                                                                             %
248 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
249 %
250 %  DestroyStreamInfo() destroys memory associated with the StreamInfo
251 %  structure.
252 %
253 %  The format of the DestroyStreamInfo method is:
254 %
255 %      StreamInfo *DestroyStreamInfo(StreamInfo *stream_info)
256 %
257 %  A description of each parameter follows:
258 %
259 %    o stream_info: the stream info.
260 %
261 */
262 MagickExport StreamInfo *DestroyStreamInfo(StreamInfo *stream_info)
263 {
264   (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
265   assert(stream_info != (StreamInfo *) NULL);
266   assert(stream_info->signature == MagickSignature);
267   if (stream_info->map != (char *) NULL)
268     stream_info->map=DestroyString(stream_info->map);
269   if (stream_info->pixels != (unsigned char *) NULL)
270     stream_info->pixels=(unsigned char *) RelinquishMagickMemory(
271       stream_info->pixels);
272   if (stream_info->stream != (Image *) NULL)
273     {
274       (void) CloseBlob(stream_info->stream);
275       stream_info->stream=DestroyImage(stream_info->stream);
276     }
277   if (stream_info->quantum_info != (QuantumInfo *) NULL)
278     stream_info->quantum_info=DestroyQuantumInfo(stream_info->quantum_info);
279   stream_info->signature=(~MagickSignature);
280   stream_info=(StreamInfo *) RelinquishMagickMemory(stream_info);
281   return(stream_info);
282 }
283 \f
284 /*
285 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
286 %                                                                             %
287 %                                                                             %
288 %                                                                             %
289 +   G e t A u t h e n t i c I n d e x e s F r o m S t r e a m                 %
290 %                                                                             %
291 %                                                                             %
292 %                                                                             %
293 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
294 %
295 %  GetAuthenticIndexesFromStream() returns the indexes associated with the
296 %  last call to QueueAuthenticPixelsStream() or GetAuthenticPixelsStream().
297 %
298 %  The format of the GetAuthenticIndexesFromStream() method is:
299 %
300 %      IndexPacket *GetAuthenticIndexesFromStream(const Image *image)
301 %
302 %  A description of each parameter follows:
303 %
304 %    o image: the image.
305 %
306 */
307 static IndexPacket *GetAuthenticIndexesFromStream(const Image *image)
308 {
309   CacheInfo
310     *cache_info;
311
312   assert(image != (Image *) NULL);
313   assert(image->signature == MagickSignature);
314   if (image->debug != MagickFalse)
315     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
316   cache_info=(CacheInfo *) image->cache;
317   assert(cache_info->signature == MagickSignature);
318   return(cache_info->indexes);
319 }
320 \f
321 /*
322 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
323 %                                                                             %
324 %                                                                             %
325 %                                                                             %
326 +   G e t A u t h e n t i c P i x e l S t r e a m                             %
327 %                                                                             %
328 %                                                                             %
329 %                                                                             %
330 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
331 %
332 %  GetAuthenticPixelsStream() gets pixels from the in-memory or disk pixel
333 %  cache as defined by the geometry parameters.   A pointer to the pixels is
334 %  returned if the pixels are transferred, otherwise a NULL is returned.  For
335 %  streams this method is a no-op.
336 %
337 %  The format of the GetAuthenticPixelsStream() method is:
338 %
339 %      PixelPacket *GetAuthenticPixelsStream(Image *image,const long x,
340 %        const long y,const unsigned long columns,const unsigned long rows,
341 %        ExceptionInfo *exception)
342 %
343 %  A description of each parameter follows:
344 %
345 %    o image: the image.
346 %
347 %    o x,y,columns,rows:  These values define the perimeter of a region of
348 %      pixels.
349 %
350 %    o exception: return any errors or warnings in this structure.
351 %
352 */
353 static PixelPacket *GetAuthenticPixelsStream(Image *image,const long x,
354   const long y,const unsigned long columns,const unsigned long rows,
355   ExceptionInfo *exception)
356 {
357   PixelPacket
358     *pixels;
359
360   assert(image != (Image *) NULL);
361   assert(image->signature == MagickSignature);
362   if (image->debug != MagickFalse)
363     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
364   pixels=QueueAuthenticPixelsStream(image,x,y,columns,rows,exception);
365   return(pixels);
366 }
367 \f
368 /*
369 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
370 %                                                                             %
371 %                                                                             %
372 %                                                                             %
373 +   G e t A u t h e n t i c P i x e l F r o m S t e a m                       %
374 %                                                                             %
375 %                                                                             %
376 %                                                                             %
377 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
378 %
379 %  GetAuthenticPixelsFromStream() returns the pixels associated with the last
380 %  call to QueueAuthenticPixelsStream() or GetAuthenticPixelsStream().
381 %
382 %  The format of the GetAuthenticPixelsFromStream() method is:
383 %
384 %      PixelPacket *GetAuthenticPixelsFromStream(const Image image)
385 %
386 %  A description of each parameter follows:
387 %
388 %    o image: the image.
389 %
390 */
391 static PixelPacket *GetAuthenticPixelsFromStream(const Image *image)
392 {
393   CacheInfo
394     *cache_info;
395
396   assert(image != (Image *) NULL);
397   assert(image->signature == MagickSignature);
398   if (image->debug != MagickFalse)
399     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
400   cache_info=(CacheInfo *) image->cache;
401   assert(cache_info->signature == MagickSignature);
402   return(cache_info->pixels);
403 }
404 \f
405 /*
406 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
407 %                                                                             %
408 %                                                                             %
409 %                                                                             %
410 +   G e t O n e A u t h e n t i c P i x e l F r o m S t r e a m               %
411 %                                                                             %
412 %                                                                             %
413 %                                                                             %
414 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
415 %
416 %  GetOneAuthenticPixelFromStream() returns a single pixel at the specified
417 %  (x,y) location.  The image background color is returned if an error occurs.
418 %
419 %  The format of the GetOneAuthenticPixelFromStream() method is:
420 %
421 %      MagickBooleanType GetOneAuthenticPixelFromStream(const Image image,
422 %        const long x,const long y,PixelPacket *pixel,ExceptionInfo *exception)
423 %
424 %  A description of each parameter follows:
425 %
426 %    o image: the image.
427 %
428 %    o pixel: return a pixel at the specified (x,y) location.
429 %
430 %    o x,y:  These values define the location of the pixel to return.
431 %
432 %    o exception: return any errors or warnings in this structure.
433 %
434 */
435 static MagickBooleanType GetOneAuthenticPixelFromStream(Image *image,
436   const long x,const long y,PixelPacket *pixel,ExceptionInfo *exception)
437 {
438   register PixelPacket
439     *pixels;
440
441   assert(image != (Image *) NULL);
442   assert(image->signature == MagickSignature);
443   *pixel=image->background_color;
444   pixels=GetAuthenticPixelsStream(image,x,y,1,1,exception);
445   if (pixels != (PixelPacket *) NULL)
446     return(MagickFalse);
447   *pixel=(*pixels);
448   return(MagickTrue);
449 }
450 \f
451 /*
452 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
453 %                                                                             %
454 %                                                                             %
455 %                                                                             %
456 +   G e t O n e V i r t u a l P i x e l F r o m S t r e a m                   %
457 %                                                                             %
458 %                                                                             %
459 %                                                                             %
460 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
461 %
462 %  GetOneVirtualPixelFromStream() returns a single pixel at the specified
463 %  (x.y) location.  The image background color is returned if an error occurs.
464 %
465 %  The format of the GetOneVirtualPixelFromStream() method is:
466 %
467 %      MagickBooleanType GetOneVirtualPixelFromStream(const Image image,
468 %        const VirtualPixelMethod virtual_pixel_method,const long x,
469 %        const long y,PixelPacket *pixel,ExceptionInfo *exception)
470 %
471 %  A description of each parameter follows:
472 %
473 %    o image: the image.
474 %
475 %    o virtual_pixel_method: the virtual pixel method.
476 %
477 %    o x,y:  These values define the location of the pixel to return.
478 %
479 %    o pixel: return a pixel at the specified (x,y) location.
480 %
481 %    o exception: return any errors or warnings in this structure.
482 %
483 */
484 static MagickBooleanType GetOneVirtualPixelFromStream(const Image *image,
485   const VirtualPixelMethod virtual_pixel_method,const long x,const long y,
486   PixelPacket *pixel,ExceptionInfo *exception)
487 {
488   const PixelPacket
489     *pixels;
490
491   assert(image != (Image *) NULL);
492   assert(image->signature == MagickSignature);
493   *pixel=image->background_color;
494   pixels=GetVirtualPixelStream(image,virtual_pixel_method,x,y,1,1,exception);
495   if (pixels != (const PixelPacket *) NULL)
496     return(MagickFalse);
497   *pixel=(*pixels);
498   return(MagickTrue);
499 }
500 \f
501 /*
502 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
503 %                                                                             %
504 %                                                                             %
505 %                                                                             %
506 +   G e t S t r e a m I n f o C l i e n t D a t a                             %
507 %                                                                             %
508 %                                                                             %
509 %                                                                             %
510 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
511 %
512 %  GetStreamInfoClientData() gets the stream info client data.
513 %
514 %  The format of the SetStreamInfoClientData method is:
515 %
516 %      const void *GetStreamInfoClientData(StreamInfo *stream_info)
517 %
518 %  A description of each parameter follows:
519 %
520 %    o stream_info: the stream info.
521 %
522 */
523 MagickExport const void *GetStreamInfoClientData(StreamInfo *stream_info)
524 {
525   assert(stream_info != (StreamInfo *) NULL);
526   assert(stream_info->signature == MagickSignature);
527   return(stream_info->client_data);
528 }
529 \f
530 /*
531 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
532 %                                                                             %
533 %                                                                             %
534 %                                                                             %
535 +   G e t  V i r t u a l P i x e l s F r o m S t r e a m                      %
536 %                                                                             %
537 %                                                                             %
538 %                                                                             %
539 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
540 %
541 %  GetVirtualPixelsStream() returns the pixels associated with the last
542 %  call to QueueAuthenticPixelsStream() or GetVirtualPixelStream().
543 %
544 %  The format of the GetVirtualPixelsStream() method is:
545 %
546 %      const IndexPacket *GetVirtualPixelsStream(const Image *image)
547 %
548 %  A description of each parameter follows:
549 %
550 %    o pixels: return the pixels associated with the last call to
551 %      QueueAuthenticPixelsStream() or GetVirtualPixelStream().
552 %
553 %    o image: the image.
554 %
555 */
556 static const PixelPacket *GetVirtualPixelsStream(const Image *image)
557 {
558   CacheInfo
559     *cache_info;
560
561   assert(image != (Image *) NULL);
562   assert(image->signature == MagickSignature);
563   if (image->debug != MagickFalse)
564     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
565   cache_info=(CacheInfo *) image->cache;
566   assert(cache_info->signature == MagickSignature);
567   return(cache_info->pixels);
568 }
569 \f
570 /*
571 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
572 %                                                                             %
573 %                                                                             %
574 %                                                                             %
575 +   G e t V i r t u a l I n d e x e s F r o m S t r e a m                     %
576 %                                                                             %
577 %                                                                             %
578 %                                                                             %
579 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
580 %
581 %  GetVirtualIndexesFromStream() returns the indexes associated with the last
582 %  call to QueueAuthenticPixelsStream() or GetVirtualPixelStream().
583 %
584 %  The format of the GetVirtualIndexesFromStream() method is:
585 %
586 %      const IndexPacket *GetVirtualIndexesFromStream(const Image *image)
587 %
588 %  A description of each parameter follows:
589 %
590 %    o image: the image.
591 %
592 */
593 static const IndexPacket *GetVirtualIndexesFromStream(const Image *image)
594 {
595   CacheInfo
596     *cache_info;
597
598   assert(image != (Image *) NULL);
599   assert(image->signature == MagickSignature);
600   if (image->debug != MagickFalse)
601     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
602   cache_info=(CacheInfo *) image->cache;
603   assert(cache_info->signature == MagickSignature);
604   return(cache_info->indexes);
605 }
606 \f
607 /*
608 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
609 %                                                                             %
610 %                                                                             %
611 %                                                                             %
612 +   G e t V i r t u a l P i x e l S t r e a m                                 %
613 %                                                                             %
614 %                                                                             %
615 %                                                                             %
616 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
617 %
618 %  GetVirtualPixelStream() gets pixels from the in-memory or disk pixel cache as
619 %  defined by the geometry parameters.   A pointer to the pixels is returned if
620 %  the pixels are transferred, otherwise a NULL is returned.  For streams this
621 %  method is a no-op.
622 %
623 %  The format of the GetVirtualPixelStream() method is:
624 %
625 %      const PixelPacket *GetVirtualPixelStream(const Image *image,
626 %        const VirtualPixelMethod virtual_pixel_method,const long x,
627 %        const long y,const unsigned long columns,const unsigned long rows,
628 %        ExceptionInfo *exception)
629 %
630 %  A description of each parameter follows:
631 %
632 %    o image: the image.
633 %
634 %    o virtual_pixel_method: the virtual pixel method.
635 %
636 %    o x,y,columns,rows:  These values define the perimeter of a region of
637 %      pixels.
638 %
639 %    o exception: return any errors or warnings in this structure.
640 %
641 */
642
643 static inline MagickBooleanType AcquireStreamPixels(CacheInfo *cache_info,
644   ExceptionInfo *exception)
645 {
646   if (cache_info->length != (MagickSizeType) ((size_t) cache_info->length))
647     return(MagickFalse);
648   cache_info->mapped=MagickFalse;
649   cache_info->pixels=(PixelPacket *) AcquireMagickMemory((size_t)
650     cache_info->length);
651   if (cache_info->pixels == (PixelPacket *) NULL)
652     {
653       cache_info->mapped=MagickTrue;
654       cache_info->pixels=(PixelPacket *) MapBlob(-1,IOMode,0,(size_t)
655         cache_info->length);
656     }
657   if (cache_info->pixels == (PixelPacket *) NULL)
658     {
659       (void) ThrowMagickException(exception,GetMagickModule(),
660         ResourceLimitError,"MemoryAllocationFailed","`%s'",
661         cache_info->filename);
662       return(MagickFalse);
663     }
664   return(MagickTrue);
665 }
666
667 static const PixelPacket *GetVirtualPixelStream(const Image *image,
668   const VirtualPixelMethod magick_unused(virtual_pixel_method),const long x,
669   const long y,const unsigned long columns,const unsigned long rows,
670   ExceptionInfo *exception)
671 {
672   CacheInfo
673     *cache_info;
674
675   MagickBooleanType
676     status;
677
678   MagickSizeType
679     number_pixels;
680
681   size_t
682     length;
683
684   /*
685     Validate pixel cache geometry.
686   */
687   assert(image != (const Image *) NULL);
688   assert(image->signature == MagickSignature);
689   if (image->debug != MagickFalse)
690     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
691   if ((x < 0) || (y < 0) || ((x+(long) columns) > (long) image->columns) ||
692       ((y+(long) rows) > (long) image->rows) || (columns == 0) || (rows == 0))
693     {
694       (void) ThrowMagickException(exception,GetMagickModule(),StreamError,
695         "ImageDoesNotContainTheStreamGeometry","`%s'",image->filename);
696       return((PixelPacket *) NULL);
697     }
698   cache_info=(CacheInfo *) image->cache;
699   assert(cache_info->signature == MagickSignature);
700   /*
701     Pixels are stored in a temporary buffer until they are synced to the cache.
702   */
703   number_pixels=(MagickSizeType) columns*rows;
704   length=(size_t) number_pixels*sizeof(PixelPacket);
705   if ((image->storage_class == PseudoClass) ||
706       (image->colorspace == CMYKColorspace))
707     length+=number_pixels*sizeof(IndexPacket);
708   if (cache_info->pixels == (PixelPacket *) NULL)
709     {
710       cache_info->length=length;
711       status=AcquireStreamPixels(cache_info,exception);
712       if (status == MagickFalse)
713         return((PixelPacket *) NULL);
714     }
715   else
716     if (cache_info->length != length)
717       {
718         RelinquishStreamPixels(cache_info);
719         cache_info->length=length;
720         status=AcquireStreamPixels(cache_info,exception);
721         if (status == MagickFalse)
722           return((PixelPacket *) NULL);
723       }
724   cache_info->indexes=(IndexPacket *) NULL;
725   if ((image->storage_class == PseudoClass) ||
726       (image->colorspace == CMYKColorspace))
727     cache_info->indexes=(IndexPacket *) (cache_info->pixels+number_pixels);
728   return(cache_info->pixels);
729 }
730 \f
731 /*
732 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
733 %                                                                             %
734 %                                                                             %
735 %                                                                             %
736 +   O p e n S t r e a m                                                       %
737 %                                                                             %
738 %                                                                             %
739 %                                                                             %
740 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
741 %
742 %  OpenStream() opens a stream for writing by the StreamImage() method.
743 %
744 %  The format of the OpenStream method is:
745 %
746 %       MagickBooleanType OpenStream(const ImageInfo *image_info,
747 %        StreamInfo *stream_info,const char *filename,ExceptionInfo *exception)
748 %
749 %  A description of each parameter follows:
750 %
751 %    o image_info: the image info.
752 %
753 %    o stream_info: the stream info.
754 %
755 %    o filename: the stream filename.
756 %
757 %    o exception: return any errors or warnings in this structure.
758 %
759 */
760 MagickExport MagickBooleanType OpenStream(const ImageInfo *image_info,
761   StreamInfo *stream_info,const char *filename,ExceptionInfo *exception)
762 {
763   MagickBooleanType
764     status;
765
766   (void) CopyMagickString(stream_info->stream->filename,filename,MaxTextExtent);
767   status=OpenBlob(image_info,stream_info->stream,WriteBinaryBlobMode,exception);
768   return(status);
769 }
770 \f
771 /*
772 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
773 %                                                                             %
774 %                                                                             %
775 %                                                                             %
776 +   Q u e u e A u t h e n t i c P i x e l s S t r e a m                       %
777 %                                                                             %
778 %                                                                             %
779 %                                                                             %
780 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
781 %
782 %  QueueAuthenticPixelsStream() allocates an area to store image pixels as
783 %  defined by the region rectangle and returns a pointer to the area.  This
784 %  area is subsequently transferred from the pixel cache with method
785 %  SyncAuthenticPixelsStream().  A pointer to the pixels is returned if the
786 %  pixels are transferred, otherwise a NULL is returned.
787 %
788 %  The format of the QueueAuthenticPixelsStream() method is:
789 %
790 %      PixelPacket *QueueAuthenticPixelsStream(Image *image,const long x,
791 %        const long y,const unsigned long columns,const unsigned long rows,
792 %        ExceptionInfo *exception)
793 %
794 %  A description of each parameter follows:
795 %
796 %    o image: the image.
797 %
798 %    o x,y,columns,rows:  These values define the perimeter of a region of
799 %      pixels.
800 %
801 */
802 static PixelPacket *QueueAuthenticPixelsStream(Image *image,const long x,
803   const long y,const unsigned long columns,const unsigned long rows,
804   ExceptionInfo *exception)
805 {
806   CacheInfo
807     *cache_info;
808
809   MagickSizeType
810     number_pixels;
811
812   size_t
813     length;
814
815   StreamHandler
816     stream_handler;
817
818   /*
819     Validate pixel cache geometry.
820   */
821   assert(image != (Image *) NULL);
822   if ((x < 0) || (y < 0) || ((x+(long) columns) > (long) image->columns) ||
823       ((y+(long) rows) > (long) image->rows) || (columns == 0) || (rows == 0))
824     {
825       (void) ThrowMagickException(exception,GetMagickModule(),StreamError,
826         "ImageDoesNotContainTheStreamGeometry","`%s'",image->filename);
827       return((PixelPacket *) NULL);
828     }
829   stream_handler=GetBlobStreamHandler(image);
830   if (stream_handler == (StreamHandler) NULL)
831     {
832       (void) ThrowMagickException(exception,GetMagickModule(),StreamError,
833         "NoStreamHandlerIsDefined","`%s'",image->filename);
834       return((PixelPacket *) NULL);
835     }
836   cache_info=(CacheInfo *) image->cache;
837   assert(cache_info->signature == MagickSignature);
838   if ((image->storage_class != GetPixelCacheStorageClass(image->cache)) ||
839       (image->colorspace != GetPixelCacheColorspace(image->cache)))
840     {
841       if (GetPixelCacheStorageClass(image->cache) == UndefinedClass)
842         (void) stream_handler(image,(const void *) NULL,(size_t)
843           cache_info->columns);
844       cache_info->storage_class=image->storage_class;
845       cache_info->colorspace=image->colorspace;
846       cache_info->columns=image->columns;
847       cache_info->rows=image->rows;
848       image->cache=cache_info;
849     }
850   /*
851     Pixels are stored in a temporary buffer until they are synced to the cache.
852   */
853   cache_info->columns=columns;
854   cache_info->rows=rows;
855   number_pixels=(MagickSizeType) columns*rows;
856   length=(size_t) number_pixels*sizeof(PixelPacket);
857   if ((image->storage_class == PseudoClass) ||
858       (image->colorspace == CMYKColorspace))
859     length+=number_pixels*sizeof(IndexPacket);
860   if (cache_info->pixels == (PixelPacket *) NULL)
861     {
862       cache_info->pixels=(PixelPacket *) AcquireMagickMemory(length);
863       cache_info->length=(MagickSizeType) length;
864     }
865   else
866     if (cache_info->length < (MagickSizeType) length)
867       {
868         cache_info->pixels=(PixelPacket *) ResizeMagickMemory(
869           cache_info->pixels,length);
870         cache_info->length=(MagickSizeType) length;
871       }
872   if (cache_info->pixels == (void *) NULL)
873     return((PixelPacket *) NULL);
874   cache_info->indexes=(IndexPacket *) NULL;
875   if ((image->storage_class == PseudoClass) ||
876       (image->colorspace == CMYKColorspace))
877     cache_info->indexes=(IndexPacket *) (cache_info->pixels+number_pixels);
878   return(cache_info->pixels);
879 }
880 \f
881 /*
882 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
883 %                                                                             %
884 %                                                                             %
885 %                                                                             %
886 %   R e a d S t r e a m                                                       %
887 %                                                                             %
888 %                                                                             %
889 %                                                                             %
890 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
891 %
892 %  ReadStream() makes the image pixels available to a user supplied callback
893 %  method immediately upon reading a scanline with the ReadImage() method.
894 %
895 %  The format of the ReadStream() method is:
896 %
897 %      Image *ReadStream(const ImageInfo *image_info,StreamHandler stream,
898 %        ExceptionInfo *exception)
899 %
900 %  A description of each parameter follows:
901 %
902 %    o image_info: the image info.
903 %
904 %    o stream: a callback method.
905 %
906 %    o exception: return any errors or warnings in this structure.
907 %
908 */
909 MagickExport Image *ReadStream(const ImageInfo *image_info,StreamHandler stream,
910   ExceptionInfo *exception)
911 {
912   CacheMethods
913     cache_methods;
914
915   Image
916     *image;
917
918   ImageInfo
919     *read_info;
920
921   /*
922     Stream image pixels.
923   */
924   assert(image_info != (ImageInfo *) NULL);
925   assert(image_info->signature == MagickSignature);
926   if (image_info->debug != MagickFalse)
927     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
928       image_info->filename);
929   assert(exception != (ExceptionInfo *) NULL);
930   assert(exception->signature == MagickSignature);
931   read_info=CloneImageInfo(image_info);
932   read_info->cache=AcquirePixelCache(0);
933   GetPixelCacheMethods(&cache_methods);
934   cache_methods.get_virtual_pixel_handler=GetVirtualPixelStream;
935   cache_methods.get_virtual_indexes_from_handler=GetVirtualIndexesFromStream;
936   cache_methods.get_virtual_pixels_handler=GetVirtualPixelsStream;
937   cache_methods.get_authentic_pixels_handler=GetAuthenticPixelsStream;
938   cache_methods.queue_authentic_pixels_handler=QueueAuthenticPixelsStream;
939   cache_methods.sync_authentic_pixels_handler=SyncAuthenticPixelsStream;
940   cache_methods.get_authentic_pixels_from_handler=GetAuthenticPixelsFromStream;
941   cache_methods.get_authentic_indexes_from_handler=
942     GetAuthenticIndexesFromStream;
943   cache_methods.get_one_virtual_pixel_from_handler=GetOneVirtualPixelFromStream;
944   cache_methods.get_one_authentic_pixel_from_handler=
945     GetOneAuthenticPixelFromStream;
946   cache_methods.destroy_pixel_handler=DestroyPixelStream;
947   SetPixelCacheMethods(read_info->cache,&cache_methods);
948   read_info->stream=stream;
949   image=ReadImage(read_info,exception);
950   read_info=DestroyImageInfo(read_info);
951   return(image);
952 }
953 \f
954 /*
955 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
956 %                                                                             %
957 %                                                                             %
958 %                                                                             %
959 +   S e t S t r e a m I n f o C l i e n t D a t a                             %
960 %                                                                             %
961 %                                                                             %
962 %                                                                             %
963 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
964 %
965 %  SetStreamInfoClientData() sets the stream info client data.
966 %
967 %  The format of the SetStreamInfoClientData method is:
968 %
969 %      void SetStreamInfoClientData(StreamInfo *stream_info,
970 %        const void *client_data)
971 %
972 %  A description of each parameter follows:
973 %
974 %    o stream_info: the stream info.
975 %
976 %    o client_data: the client data.
977 %
978 */
979 MagickExport void SetStreamInfoClientData(StreamInfo *stream_info,
980   const void *client_data)
981 {
982   assert(stream_info != (StreamInfo *) NULL);
983   assert(stream_info->signature == MagickSignature);
984   stream_info->client_data=client_data;
985 }
986 \f
987 /*
988 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
989 %                                                                             %
990 %                                                                             %
991 %                                                                             %
992 +   S e t S t r e a m I n f o M a p                                           %
993 %                                                                             %
994 %                                                                             %
995 %                                                                             %
996 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
997 %
998 %  SetStreamInfoMap() sets the stream info map member.
999 %
1000 %  The format of the SetStreamInfoMap method is:
1001 %
1002 %      void SetStreamInfoMap(StreamInfo *stream_info,const char *map)
1003 %
1004 %  A description of each parameter follows:
1005 %
1006 %    o stream_info: the stream info.
1007 %
1008 %    o map: the map.
1009 %
1010 */
1011 MagickExport void SetStreamInfoMap(StreamInfo *stream_info,const char *map)
1012 {
1013   assert(stream_info != (StreamInfo *) NULL);
1014   assert(stream_info->signature == MagickSignature);
1015   (void) CloneString(&stream_info->map,map);
1016 }
1017 \f
1018 /*
1019 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1020 %                                                                             %
1021 %                                                                             %
1022 %                                                                             %
1023 +   S e t S t r e a m I n f o S t o r a g e T y p e                           %
1024 %                                                                             %
1025 %                                                                             %
1026 %                                                                             %
1027 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1028 %
1029 %  SetStreamInfoStorageType() sets the stream info storage type member.
1030 %
1031 %  The format of the SetStreamInfoStorageType method is:
1032 %
1033 %      void SetStreamInfoStorageType(StreamInfo *stream_info,
1034 %        const StoreageType *storage_type)
1035 %
1036 %  A description of each parameter follows:
1037 %
1038 %    o stream_info: the stream info.
1039 %
1040 %    o storage_type: the storage type.
1041 %
1042 */
1043 MagickExport void SetStreamInfoStorageType(StreamInfo *stream_info,
1044   const StorageType storage_type)
1045 {
1046   assert(stream_info != (StreamInfo *) NULL);
1047   assert(stream_info->signature == MagickSignature);
1048   stream_info->storage_type=storage_type;
1049 }
1050 \f
1051 /*
1052 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1053 %                                                                             %
1054 %                                                                             %
1055 %                                                                             %
1056 +   S t r e a m I m a g e                                                     %
1057 %                                                                             %
1058 %                                                                             %
1059 %                                                                             %
1060 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1061 %
1062 %  StreamImage() streams pixels from an image and writes them in a user
1063 %  defined format and storage type (e.g. RGBA as 8-bit unsigned char).
1064 %
1065 %  The format of he wStreamImage() method is:
1066 %
1067 %      Image *StreamImage(const ImageInfo *image_info,
1068 %        StreamInfo *stream_info,ExceptionInfo *exception)
1069 %
1070 %  A description of each parameter follows:
1071 %
1072 %    o image_info: the image info.
1073 %
1074 %    o stream_info: the stream info.
1075 %
1076 %    o exception: return any errors or warnings in this structure.
1077 %
1078 */
1079
1080 #if defined(__cplusplus) || defined(c_plusplus)
1081 extern "C" {
1082 #endif
1083
1084 static size_t WriteStreamImage(const Image *image,const void *pixels,
1085   const size_t columns)
1086 {
1087   CacheInfo
1088     *cache_info;
1089
1090   RectangleInfo
1091     extract_info;
1092
1093   size_t
1094     length,
1095     packet_size;
1096
1097   ssize_t
1098     count;
1099
1100   StreamInfo
1101     *stream_info;
1102
1103   stream_info=(StreamInfo *) image->client_data;
1104   switch (stream_info->storage_type)
1105   {
1106     default: packet_size=sizeof(char); break;
1107     case CharPixel: packet_size=sizeof(char); break;
1108     case DoublePixel: packet_size=sizeof(double); break;
1109     case FloatPixel: packet_size=sizeof(float); break;
1110     case IntegerPixel: packet_size=sizeof(int); break;
1111     case LongPixel: packet_size=sizeof(long); break;
1112     case QuantumPixel: packet_size=sizeof(Quantum); break;
1113     case ShortPixel: packet_size=sizeof(unsigned short); break;
1114   }
1115   cache_info=(CacheInfo *) image->cache;
1116   assert(cache_info->signature == MagickSignature);
1117   packet_size*=strlen(stream_info->map);
1118   length=packet_size*cache_info->columns*cache_info->rows;
1119   if (image != stream_info->image)
1120     {
1121       ImageInfo
1122         *write_info;
1123
1124       /*
1125         Prepare stream for writing.
1126       */
1127       stream_info->pixels=(unsigned char *) ResizeQuantumMemory(
1128         stream_info->pixels,length,sizeof(*stream_info->pixels));
1129       if (pixels == (unsigned char *) NULL)
1130         return(0);
1131       stream_info->image=image;
1132       write_info=CloneImageInfo(stream_info->image_info);
1133       (void) SetImageInfo(write_info,1,stream_info->exception);
1134       if (write_info->extract != (char *) NULL)
1135         (void) ParseAbsoluteGeometry(write_info->extract,
1136           &stream_info->extract_info);
1137       stream_info->y=0;
1138       write_info=DestroyImageInfo(write_info);
1139     }
1140   extract_info=stream_info->extract_info;
1141   if ((extract_info.width == 0) ||
1142       (extract_info.height == 0))
1143     {
1144       /*
1145         Write all pixels to stream.
1146       */
1147       (void) StreamImagePixels(stream_info,image,stream_info->exception);
1148       count=WriteBlob(stream_info->stream,length,stream_info->pixels);
1149       stream_info->y++;
1150       return(count == 0 ? 0 : columns);
1151     }
1152   if ((stream_info->y < extract_info.y) ||
1153       (stream_info->y >= (long) (extract_info.y+extract_info.height)))
1154     {
1155       stream_info->y++;
1156       return(columns);
1157     }
1158   /*
1159     Write a portion of the pixel row to the stream.
1160   */
1161   (void) StreamImagePixels(stream_info,image,stream_info->exception);
1162   length=packet_size*extract_info.width;
1163   count=WriteBlob(stream_info->stream,length,stream_info->pixels+
1164     packet_size*extract_info.x);
1165   stream_info->y++;
1166   return(count == 0 ? 0 : columns);
1167 }
1168
1169 #if defined(__cplusplus) || defined(c_plusplus)
1170 }
1171 #endif
1172
1173 MagickExport Image *StreamImage(const ImageInfo *image_info,
1174   StreamInfo *stream_info,ExceptionInfo *exception)
1175 {
1176   Image
1177     *image;
1178
1179   ImageInfo
1180     *read_info;
1181
1182   assert(image_info != (const ImageInfo *) NULL);
1183   assert(image_info->signature == MagickSignature);
1184   if (image_info->debug != MagickFalse)
1185     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
1186       image_info->filename);
1187   assert(stream_info != (StreamInfo *) NULL);
1188   assert(stream_info->signature == MagickSignature);
1189   assert(exception != (ExceptionInfo *) NULL);
1190   read_info=CloneImageInfo(image_info);
1191   stream_info->image_info=image_info;
1192   stream_info->exception=exception;
1193   read_info->client_data=(void *) stream_info;
1194   image=ReadStream(read_info,&WriteStreamImage,exception);
1195   read_info=DestroyImageInfo(read_info);
1196   stream_info->quantum_info=AcquireQuantumInfo(image_info,image);
1197   if (stream_info->quantum_info == (QuantumInfo *) NULL)
1198     image=DestroyImage(image);
1199   return(image);
1200 }
1201 \f
1202 /*
1203 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1204 %                                                                             %
1205 %                                                                             %
1206 %                                                                             %
1207 +   S t r e a m I m a g e P i x e l s                                         %
1208 %                                                                             %
1209 %                                                                             %
1210 %                                                                             %
1211 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1212 %
1213 %  StreamImagePixels() extracts pixel data from an image and returns it in the
1214 %  stream_info->pixels structure in the format as defined by
1215 %  stream_info->quantum_info->map and stream_info->quantum_info->storage_type.
1216 %
1217 %  The format of the StreamImagePixels method is:
1218 %
1219 %      MagickBooleanType StreamImagePixels(const StreamInfo *stream_info,
1220 %        const Image *image,ExceptionInfo *exception)
1221 %
1222 %  A description of each parameter follows:
1223 %
1224 %    o stream_info: the stream info.
1225 %
1226 %    o image: the image.
1227 %
1228 %    o exception: return any errors or warnings in this structure.
1229 %
1230 */
1231 static MagickBooleanType StreamImagePixels(const StreamInfo *stream_info,
1232   const Image *image,ExceptionInfo *exception)
1233 {
1234   QuantumInfo
1235     *quantum_info;
1236
1237   QuantumType
1238     *quantum_map;
1239
1240   register long
1241     i,
1242     x;
1243
1244   register const PixelPacket
1245     *p;
1246
1247   register IndexPacket
1248     *indexes;
1249
1250   size_t
1251     length;
1252
1253   assert(stream_info != (StreamInfo *) NULL);
1254   assert(stream_info->signature == MagickSignature);
1255   assert(image != (Image *) NULL);
1256   assert(image->signature == MagickSignature);
1257   if (image->debug != MagickFalse)
1258     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1259   length=strlen(stream_info->map);
1260   quantum_map=(QuantumType *) AcquireQuantumMemory(length,sizeof(*quantum_map));
1261   if (quantum_map == (QuantumType *) NULL)
1262     {
1263       (void) ThrowMagickException(exception,GetMagickModule(),
1264         ResourceLimitError,"MemoryAllocationFailed","`%s'",image->filename);
1265       return(MagickFalse);
1266     }
1267   for (i=0; i < (long) length; i++)
1268   {
1269     switch (stream_info->map[i])
1270     {
1271       case 'A':
1272       case 'a':
1273       {
1274         quantum_map[i]=AlphaQuantum;
1275         break;
1276       }
1277       case 'B':
1278       case 'b':
1279       {
1280         quantum_map[i]=BlueQuantum;
1281         break;
1282       }
1283       case 'C':
1284       case 'c':
1285       {
1286         quantum_map[i]=CyanQuantum;
1287         if (image->colorspace == CMYKColorspace)
1288           break;
1289         quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
1290         (void) ThrowMagickException(exception,GetMagickModule(),ImageError,
1291           "ColorSeparatedImageRequired","`%s'",stream_info->map);
1292         return(MagickFalse);
1293       }
1294       case 'g':
1295       case 'G':
1296       {
1297         quantum_map[i]=GreenQuantum;
1298         break;
1299       }
1300       case 'I':
1301       case 'i':
1302       {
1303         quantum_map[i]=IndexQuantum;
1304         break;
1305       }
1306       case 'K':
1307       case 'k':
1308       {
1309         quantum_map[i]=BlackQuantum;
1310         if (image->colorspace == CMYKColorspace)
1311           break;
1312         quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
1313         (void) ThrowMagickException(exception,GetMagickModule(),ImageError,
1314           "ColorSeparatedImageRequired","`%s'",stream_info->map);
1315         return(MagickFalse);
1316       }
1317       case 'M':
1318       case 'm':
1319       {
1320         quantum_map[i]=MagentaQuantum;
1321         if (image->colorspace == CMYKColorspace)
1322           break;
1323         quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
1324         (void) ThrowMagickException(exception,GetMagickModule(),ImageError,
1325           "ColorSeparatedImageRequired","`%s'",stream_info->map);
1326         return(MagickFalse);
1327       }
1328       case 'o':
1329       case 'O':
1330       {
1331         quantum_map[i]=OpacityQuantum;
1332         break;
1333       }
1334       case 'P':
1335       case 'p':
1336       {
1337         quantum_map[i]=UndefinedQuantum;
1338         break;
1339       }
1340       case 'R':
1341       case 'r':
1342       {
1343         quantum_map[i]=RedQuantum;
1344         break;
1345       }
1346       case 'Y':
1347       case 'y':
1348       {
1349         quantum_map[i]=YellowQuantum;
1350         if (image->colorspace == CMYKColorspace)
1351           break;
1352         quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
1353         (void) ThrowMagickException(exception,GetMagickModule(),ImageError,
1354           "ColorSeparatedImageRequired","`%s'",stream_info->map);
1355         return(MagickFalse);
1356       }
1357       default:
1358       {
1359         quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
1360         (void) ThrowMagickException(exception,GetMagickModule(),OptionError,
1361           "UnrecognizedPixelMap","`%s'",stream_info->map);
1362         return(MagickFalse);
1363       }
1364     }
1365   }
1366   quantum_info=stream_info->quantum_info;
1367   switch (stream_info->storage_type)
1368   {
1369     case CharPixel:
1370     {
1371       register unsigned char
1372         *q;
1373
1374       q=(unsigned char *) stream_info->pixels;
1375       if (LocaleCompare(stream_info->map,"BGR") == 0)
1376         {
1377           p=GetAuthenticPixelQueue(image);
1378           if (p == (const PixelPacket *) NULL)
1379             break;
1380           for (x=0; x < (long) GetImageExtent(image); x++)
1381           {
1382             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1383             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1384             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1385             p++;
1386           }
1387           break;
1388         }
1389       if (LocaleCompare(stream_info->map,"BGRA") == 0)
1390         {
1391           p=GetAuthenticPixelQueue(image);
1392           if (p == (const PixelPacket *) NULL)
1393             break;
1394           for (x=0; x < (long) GetImageExtent(image); x++)
1395           {
1396             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1397             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1398             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1399             *q++=ScaleQuantumToChar((Quantum) (GetAlphaPixelComponent(p)));
1400             p++;
1401           }
1402           break;
1403         }
1404       if (LocaleCompare(stream_info->map,"BGRP") == 0)
1405         {
1406           p=GetAuthenticPixelQueue(image);
1407           if (p == (const PixelPacket *) NULL)
1408               break;
1409           for (x=0; x < (long) GetImageExtent(image); x++)
1410           {
1411             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1412             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1413             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1414             *q++=ScaleQuantumToChar((Quantum) 0);
1415             p++;
1416           }
1417           break;
1418         }
1419       if (LocaleCompare(stream_info->map,"I") == 0)
1420         {
1421           p=GetAuthenticPixelQueue(image);
1422           if (p == (const PixelPacket *) NULL)
1423             break;
1424           for (x=0; x < (long) GetImageExtent(image); x++)
1425           {
1426             *q++=ScaleQuantumToChar(PixelIntensityToQuantum(p));
1427             p++;
1428           }
1429           break;
1430         }
1431       if (LocaleCompare(stream_info->map,"RGB") == 0)
1432         {
1433           p=GetAuthenticPixelQueue(image);
1434           if (p == (const PixelPacket *) NULL)
1435             break;
1436           for (x=0; x < (long) GetImageExtent(image); x++)
1437           {
1438             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1439             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1440             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1441             p++;
1442           }
1443           break;
1444         }
1445       if (LocaleCompare(stream_info->map,"RGBA") == 0)
1446         {
1447           p=GetAuthenticPixelQueue(image);
1448           if (p == (const PixelPacket *) NULL)
1449             break;
1450           for (x=0; x < (long) GetImageExtent(image); x++)
1451           {
1452             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1453             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1454             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1455             *q++=ScaleQuantumToChar((Quantum) (GetAlphaPixelComponent(p)));
1456             p++;
1457           }
1458           break;
1459         }
1460       if (LocaleCompare(stream_info->map,"RGBP") == 0)
1461         {
1462           p=GetAuthenticPixelQueue(image);
1463           if (p == (const PixelPacket *) NULL)
1464             break;
1465           for (x=0; x < (long) GetImageExtent(image); x++)
1466           {
1467             *q++=ScaleQuantumToChar(GetRedPixelComponent(p));
1468             *q++=ScaleQuantumToChar(GetGreenPixelComponent(p));
1469             *q++=ScaleQuantumToChar(GetBluePixelComponent(p));
1470             *q++=ScaleQuantumToChar((Quantum) 0);
1471             p++;
1472           }
1473           break;
1474         }
1475       p=GetAuthenticPixelQueue(image);
1476       if (p == (const PixelPacket *) NULL)
1477         break;
1478       indexes=GetAuthenticIndexQueue(image);
1479       for (x=0; x < (long) GetImageExtent(image); x++)
1480       {
1481         for (i=0; i < (long) length; i++)
1482         {
1483           *q=0;
1484           switch (quantum_map[i])
1485           {
1486             case RedQuantum:
1487             case CyanQuantum:
1488             {
1489               *q=ScaleQuantumToChar(GetRedPixelComponent(p));
1490               break;
1491             }
1492             case GreenQuantum:
1493             case MagentaQuantum:
1494             {
1495               *q=ScaleQuantumToChar(GetGreenPixelComponent(p));
1496               break;
1497             }
1498             case BlueQuantum:
1499             case YellowQuantum:
1500             {
1501               *q=ScaleQuantumToChar(GetBluePixelComponent(p));
1502               break;
1503             }
1504             case AlphaQuantum:
1505             {
1506               *q=ScaleQuantumToChar((Quantum) (GetAlphaPixelComponent(p)));
1507               break;
1508             }
1509             case OpacityQuantum:
1510             {
1511               *q=ScaleQuantumToChar(GetOpacityPixelComponent(p));
1512               break;
1513             }
1514             case BlackQuantum:
1515             {
1516               if (image->colorspace == CMYKColorspace)
1517                 *q=ScaleQuantumToChar(indexes[x]);
1518               break;
1519             }
1520             case IndexQuantum:
1521             {
1522               *q=ScaleQuantumToChar(PixelIntensityToQuantum(p));
1523               break;
1524             }
1525             default:
1526               break;
1527           }
1528           q++;
1529         }
1530         p++;
1531       }
1532       break;
1533     }
1534     case DoublePixel:
1535     {
1536       register double
1537         *q;
1538
1539       q=(double *) stream_info->pixels;
1540       if (LocaleCompare(stream_info->map,"BGR") == 0)
1541         {
1542           p=GetAuthenticPixelQueue(image);
1543           if (p == (const PixelPacket *) NULL)
1544             break;
1545           for (x=0; x < (long) GetImageExtent(image); x++)
1546           {
1547             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1548               quantum_info->scale+quantum_info->minimum);
1549             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1550               quantum_info->scale+quantum_info->minimum);
1551             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1552               quantum_info->scale+quantum_info->minimum);
1553             p++;
1554           }
1555           break;
1556         }
1557       if (LocaleCompare(stream_info->map,"BGRA") == 0)
1558         {
1559           p=GetAuthenticPixelQueue(image);
1560           if (p == (const PixelPacket *) NULL)
1561             break;
1562           for (x=0; x < (long) GetImageExtent(image); x++)
1563           {
1564             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1565               quantum_info->scale+quantum_info->minimum);
1566             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1567               quantum_info->scale+quantum_info->minimum);
1568             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1569               quantum_info->scale+quantum_info->minimum);
1570             *q++=(double) ((QuantumScale*GetAlphaPixelComponent(p))*
1571               quantum_info->scale+quantum_info->minimum);
1572             p++;
1573           }
1574           break;
1575         }
1576       if (LocaleCompare(stream_info->map,"BGRP") == 0)
1577         {
1578           p=GetAuthenticPixelQueue(image);
1579           if (p == (const PixelPacket *) NULL)
1580             break;
1581           for (x=0; x < (long) GetImageExtent(image); x++)
1582           {
1583             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1584               quantum_info->scale+quantum_info->minimum);
1585             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1586               quantum_info->scale+quantum_info->minimum);
1587             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1588               quantum_info->scale+quantum_info->minimum);
1589             *q++=0.0;
1590             p++;
1591           }
1592           break;
1593         }
1594       if (LocaleCompare(stream_info->map,"I") == 0)
1595         {
1596           p=GetAuthenticPixelQueue(image);
1597           if (p == (const PixelPacket *) NULL)
1598             break;
1599           for (x=0; x < (long) GetImageExtent(image); x++)
1600           {
1601             *q++=(double) ((QuantumScale*PixelIntensityToQuantum(p))*
1602               quantum_info->scale+quantum_info->minimum);
1603             p++;
1604           }
1605           break;
1606         }
1607       if (LocaleCompare(stream_info->map,"RGB") == 0)
1608         {
1609           p=GetAuthenticPixelQueue(image);
1610           if (p == (const PixelPacket *) NULL)
1611             break;
1612           for (x=0; x < (long) GetImageExtent(image); x++)
1613           {
1614             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1615               quantum_info->scale+quantum_info->minimum);
1616             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1617               quantum_info->scale+quantum_info->minimum);
1618             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1619               quantum_info->scale+quantum_info->minimum);
1620             p++;
1621           }
1622           break;
1623         }
1624       if (LocaleCompare(stream_info->map,"RGBA") == 0)
1625         {
1626           p=GetAuthenticPixelQueue(image);
1627           if (p == (const PixelPacket *) NULL)
1628             break;
1629           for (x=0; x < (long) GetImageExtent(image); x++)
1630           {
1631             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1632               quantum_info->scale+quantum_info->minimum);
1633             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1634               quantum_info->scale+quantum_info->minimum);
1635             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1636               quantum_info->scale+quantum_info->minimum);
1637             *q++=(double) ((QuantumScale*GetAlphaPixelComponent(p))*
1638               quantum_info->scale+quantum_info->minimum);
1639             p++;
1640           }
1641           break;
1642         }
1643       if (LocaleCompare(stream_info->map,"RGBP") == 0)
1644         {
1645           p=GetAuthenticPixelQueue(image);
1646           if (p == (const PixelPacket *) NULL)
1647             break;
1648           for (x=0; x < (long) GetImageExtent(image); x++)
1649           {
1650             *q++=(double) ((QuantumScale*GetRedPixelComponent(p))*
1651               quantum_info->scale+quantum_info->minimum);
1652             *q++=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1653               quantum_info->scale+quantum_info->minimum);
1654             *q++=(double) ((QuantumScale*GetBluePixelComponent(p))*
1655               quantum_info->scale+quantum_info->minimum);
1656             *q++=0.0;
1657             p++;
1658           }
1659           break;
1660         }
1661       p=GetAuthenticPixelQueue(image);
1662       if (p == (const PixelPacket *) NULL)
1663         break;
1664       indexes=GetAuthenticIndexQueue(image);
1665       for (x=0; x < (long) GetImageExtent(image); x++)
1666       {
1667         for (i=0; i < (long) length; i++)
1668         {
1669           *q=0;
1670           switch (quantum_map[i])
1671           {
1672             case RedQuantum:
1673             case CyanQuantum:
1674             {
1675               *q=(double) ((QuantumScale*GetRedPixelComponent(p))*
1676                 quantum_info->scale+quantum_info->minimum);
1677               break;
1678             }
1679             case GreenQuantum:
1680             case MagentaQuantum:
1681             {
1682               *q=(double) ((QuantumScale*GetGreenPixelComponent(p))*
1683                 quantum_info->scale+quantum_info->minimum);
1684               break;
1685             }
1686             case BlueQuantum:
1687             case YellowQuantum:
1688             {
1689               *q=(double) ((QuantumScale*GetBluePixelComponent(p))*
1690                 quantum_info->scale+quantum_info->minimum);
1691               break;
1692             }
1693             case AlphaQuantum:
1694             {
1695               *q=(double) ((QuantumScale*GetAlphaPixelComponent(p))*
1696                 quantum_info->scale+quantum_info->minimum);
1697               break;
1698             }
1699             case OpacityQuantum:
1700             {
1701               *q=(double) ((QuantumScale*GetOpacityPixelComponent(p))*
1702                 quantum_info->scale+quantum_info->minimum);
1703               break;
1704             }
1705             case BlackQuantum:
1706             {
1707               if (image->colorspace == CMYKColorspace)
1708                 *q=(double) ((QuantumScale*indexes[x])*quantum_info->scale+
1709                   quantum_info->minimum);
1710               break;
1711             }
1712             case IndexQuantum:
1713             {
1714               *q=(double) ((QuantumScale*PixelIntensityToQuantum(p))*
1715                 quantum_info->scale+quantum_info->minimum);
1716               break;
1717             }
1718             default:
1719               *q=0;
1720           }
1721           q++;
1722         }
1723         p++;
1724       }
1725       break;
1726     }
1727     case FloatPixel:
1728     {
1729       register float
1730         *q;
1731
1732       q=(float *) stream_info->pixels;
1733       if (LocaleCompare(stream_info->map,"BGR") == 0)
1734         {
1735           p=GetAuthenticPixelQueue(image);
1736           if (p == (const PixelPacket *) NULL)
1737             break;
1738           for (x=0; x < (long) GetImageExtent(image); x++)
1739           {
1740             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1741               quantum_info->scale+quantum_info->minimum);
1742             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1743               quantum_info->scale+quantum_info->minimum);
1744             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1745               quantum_info->scale+quantum_info->minimum);
1746             p++;
1747           }
1748           break;
1749         }
1750       if (LocaleCompare(stream_info->map,"BGRA") == 0)
1751         {
1752           p=GetAuthenticPixelQueue(image);
1753           if (p == (const PixelPacket *) NULL)
1754             break;
1755           for (x=0; x < (long) GetImageExtent(image); x++)
1756           {
1757             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1758               quantum_info->scale+quantum_info->minimum);
1759             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1760               quantum_info->scale+quantum_info->minimum);
1761             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1762               quantum_info->scale+quantum_info->minimum);
1763             *q++=(float) ((QuantumScale*(Quantum) (GetAlphaPixelComponent(p)))*
1764               quantum_info->scale+quantum_info->minimum);
1765             p++;
1766           }
1767           break;
1768         }
1769       if (LocaleCompare(stream_info->map,"BGRP") == 0)
1770         {
1771           p=GetAuthenticPixelQueue(image);
1772           if (p == (const PixelPacket *) NULL)
1773             break;
1774           for (x=0; x < (long) GetImageExtent(image); x++)
1775           {
1776             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1777               quantum_info->scale+quantum_info->minimum);
1778             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1779               quantum_info->scale+quantum_info->minimum);
1780             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1781               quantum_info->scale+quantum_info->minimum);
1782             *q++=0.0;
1783             p++;
1784           }
1785           break;
1786         }
1787       if (LocaleCompare(stream_info->map,"I") == 0)
1788         {
1789           p=GetAuthenticPixelQueue(image);
1790           if (p == (const PixelPacket *) NULL)
1791             break;
1792           for (x=0; x < (long) GetImageExtent(image); x++)
1793           {
1794             *q++=(float) ((QuantumScale*PixelIntensityToQuantum(p))*
1795               quantum_info->scale+quantum_info->minimum);
1796             p++;
1797           }
1798           break;
1799         }
1800       if (LocaleCompare(stream_info->map,"RGB") == 0)
1801         {
1802           p=GetAuthenticPixelQueue(image);
1803           if (p == (const PixelPacket *) NULL)
1804             break;
1805           for (x=0; x < (long) GetImageExtent(image); x++)
1806           {
1807             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1808               quantum_info->scale+quantum_info->minimum);
1809             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1810               quantum_info->scale+quantum_info->minimum);
1811             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1812               quantum_info->scale+quantum_info->minimum);
1813             p++;
1814           }
1815           break;
1816         }
1817       if (LocaleCompare(stream_info->map,"RGBA") == 0)
1818         {
1819           p=GetAuthenticPixelQueue(image);
1820           if (p == (const PixelPacket *) NULL)
1821             break;
1822           for (x=0; x < (long) GetImageExtent(image); x++)
1823           {
1824             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1825               quantum_info->scale+quantum_info->minimum);
1826             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1827               quantum_info->scale+quantum_info->minimum);
1828             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1829               quantum_info->scale+quantum_info->minimum);
1830             *q++=(float) ((QuantumScale*GetAlphaPixelComponent(p))*
1831               quantum_info->scale+quantum_info->minimum);
1832             p++;
1833           }
1834           break;
1835         }
1836       if (LocaleCompare(stream_info->map,"RGBP") == 0)
1837         {
1838           p=GetAuthenticPixelQueue(image);
1839           if (p == (const PixelPacket *) NULL)
1840             break;
1841           for (x=0; x < (long) GetImageExtent(image); x++)
1842           {
1843             *q++=(float) ((QuantumScale*GetRedPixelComponent(p))*
1844               quantum_info->scale+quantum_info->minimum);
1845             *q++=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1846               quantum_info->scale+quantum_info->minimum);
1847             *q++=(float) ((QuantumScale*GetBluePixelComponent(p))*
1848               quantum_info->scale+quantum_info->minimum);
1849             *q++=0.0;
1850             p++;
1851           }
1852           break;
1853         }
1854       p=GetAuthenticPixelQueue(image);
1855       if (p == (const PixelPacket *) NULL)
1856         break;
1857       indexes=GetAuthenticIndexQueue(image);
1858       for (x=0; x < (long) GetImageExtent(image); x++)
1859       {
1860         for (i=0; i < (long) length; i++)
1861         {
1862           *q=0;
1863           switch (quantum_map[i])
1864           {
1865             case RedQuantum:
1866             case CyanQuantum:
1867             {
1868               *q=(float) ((QuantumScale*GetRedPixelComponent(p))*
1869                 quantum_info->scale+quantum_info->minimum);
1870               break;
1871             }
1872             case GreenQuantum:
1873             case MagentaQuantum:
1874             {
1875               *q=(float) ((QuantumScale*GetGreenPixelComponent(p))*
1876                 quantum_info->scale+quantum_info->minimum);
1877               break;
1878             }
1879             case BlueQuantum:
1880             case YellowQuantum:
1881             {
1882               *q=(float) ((QuantumScale*GetBluePixelComponent(p))*
1883                 quantum_info->scale+quantum_info->minimum);
1884               break;
1885             }
1886             case AlphaQuantum:
1887             {
1888               *q=(float) ((QuantumScale*GetAlphaPixelComponent(p))*
1889                 quantum_info->scale+quantum_info->minimum);
1890               break;
1891             }
1892             case OpacityQuantum:
1893             {
1894               *q=(float) ((QuantumScale*GetOpacityPixelComponent(p))*
1895                 quantum_info->scale+quantum_info->minimum);
1896               break;
1897             }
1898             case BlackQuantum:
1899             {
1900               if (image->colorspace == CMYKColorspace)
1901                 *q=(float) ((QuantumScale*indexes[x])*quantum_info->scale+
1902                   quantum_info->minimum);
1903               break;
1904             }
1905             case IndexQuantum:
1906             {
1907               *q=(float) ((QuantumScale*PixelIntensityToQuantum(p))*
1908                 quantum_info->scale+quantum_info->minimum);
1909               break;
1910             }
1911             default:
1912               *q=0;
1913           }
1914           q++;
1915         }
1916         p++;
1917       }
1918       break;
1919     }
1920     case IntegerPixel:
1921     {
1922       register unsigned int
1923         *q;
1924
1925       q=(unsigned int *) stream_info->pixels;
1926       if (LocaleCompare(stream_info->map,"BGR") == 0)
1927         {
1928           p=GetAuthenticPixelQueue(image);
1929           if (p == (const PixelPacket *) NULL)
1930             break;
1931           for (x=0; x < (long) GetImageExtent(image); x++)
1932           {
1933             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
1934             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
1935             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
1936             p++;
1937           }
1938           break;
1939         }
1940       if (LocaleCompare(stream_info->map,"BGRA") == 0)
1941         {
1942           p=GetAuthenticPixelQueue(image);
1943           if (p == (const PixelPacket *) NULL)
1944             break;
1945           for (x=0; x < (long) GetImageExtent(image); x++)
1946           {
1947             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
1948             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
1949             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
1950             *q++=(unsigned int) ScaleQuantumToLong((Quantum) (QuantumRange-
1951               GetOpacityPixelComponent(p)));
1952             p++;
1953           }
1954           break;
1955         }
1956       if (LocaleCompare(stream_info->map,"BGRP") == 0)
1957         {
1958           p=GetAuthenticPixelQueue(image);
1959           if (p == (const PixelPacket *) NULL)
1960             break;
1961           for (x=0; x < (long) GetImageExtent(image); x++)
1962           {
1963             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
1964             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
1965             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
1966             *q++=0U;
1967             p++;
1968           }
1969           break;
1970         }
1971       if (LocaleCompare(stream_info->map,"I") == 0)
1972         {
1973           p=GetAuthenticPixelQueue(image);
1974           if (p == (const PixelPacket *) NULL)
1975             break;
1976           for (x=0; x < (long) GetImageExtent(image); x++)
1977           {
1978             *q++=(unsigned int) ScaleQuantumToLong(
1979               PixelIntensityToQuantum(p));
1980             p++;
1981           }
1982           break;
1983         }
1984       if (LocaleCompare(stream_info->map,"RGB") == 0)
1985         {
1986           p=GetAuthenticPixelQueue(image);
1987           if (p == (const PixelPacket *) NULL)
1988             break;
1989           for (x=0; x < (long) GetImageExtent(image); x++)
1990           {
1991             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
1992             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
1993             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
1994             p++;
1995           }
1996           break;
1997         }
1998       if (LocaleCompare(stream_info->map,"RGBA") == 0)
1999         {
2000           p=GetAuthenticPixelQueue(image);
2001           if (p == (const PixelPacket *) NULL)
2002             break;
2003           for (x=0; x < (long) GetImageExtent(image); x++)
2004           {
2005             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
2006             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
2007             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
2008             *q++=(unsigned int) ScaleQuantumToLong((Quantum)
2009               (GetAlphaPixelComponent(p)));
2010             p++;
2011           }
2012           break;
2013         }
2014       if (LocaleCompare(stream_info->map,"RGBP") == 0)
2015         {
2016           p=GetAuthenticPixelQueue(image);
2017           if (p == (const PixelPacket *) NULL)
2018             break;
2019           for (x=0; x < (long) GetImageExtent(image); x++)
2020           {
2021             *q++=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
2022             *q++=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
2023             *q++=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
2024             *q++=0U;
2025             p++;
2026           }
2027           break;
2028         }
2029       p=GetAuthenticPixelQueue(image);
2030       if (p == (const PixelPacket *) NULL)
2031         break;
2032       indexes=GetAuthenticIndexQueue(image);
2033       for (x=0; x < (long) GetImageExtent(image); x++)
2034       {
2035         for (i=0; i < (long) length; i++)
2036         {
2037           *q=0;
2038           switch (quantum_map[i])
2039           {
2040             case RedQuantum:
2041             case CyanQuantum:
2042             {
2043               *q=(unsigned int) ScaleQuantumToLong(GetRedPixelComponent(p));
2044               break;
2045             }
2046             case GreenQuantum:
2047             case MagentaQuantum:
2048             {
2049               *q=(unsigned int) ScaleQuantumToLong(GetGreenPixelComponent(p));
2050               break;
2051             }
2052             case BlueQuantum:
2053             case YellowQuantum:
2054             {
2055               *q=(unsigned int) ScaleQuantumToLong(GetBluePixelComponent(p));
2056               break;
2057             }
2058             case AlphaQuantum:
2059             {
2060               *q=(unsigned int) ScaleQuantumToLong((Quantum) (QuantumRange-
2061                 GetOpacityPixelComponent(p)));
2062               break;
2063             }
2064             case OpacityQuantum:
2065             {
2066               *q=(unsigned int) ScaleQuantumToLong(GetOpacityPixelComponent(p));
2067               break;
2068             }
2069             case BlackQuantum:
2070             {
2071               if (image->colorspace == CMYKColorspace)
2072                 *q=(unsigned int) ScaleQuantumToLong(indexes[x]);
2073               break;
2074             }
2075             case IndexQuantum:
2076             {
2077               *q=(unsigned int)
2078                 ScaleQuantumToLong(PixelIntensityToQuantum(p));
2079               break;
2080             }
2081             default:
2082               *q=0;
2083           }
2084           q++;
2085         }
2086         p++;
2087       }
2088       break;
2089     }
2090     case LongPixel:
2091     {
2092       register unsigned long
2093         *q;
2094
2095       q=(unsigned long *) stream_info->pixels;
2096       if (LocaleCompare(stream_info->map,"BGR") == 0)
2097         {
2098           p=GetAuthenticPixelQueue(image);
2099           if (p == (const PixelPacket *) NULL)
2100             break;
2101           for (x=0; x < (long) GetImageExtent(image); x++)
2102           {
2103             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2104             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2105             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2106             p++;
2107           }
2108           break;
2109         }
2110       if (LocaleCompare(stream_info->map,"BGRA") == 0)
2111         {
2112           p=GetAuthenticPixelQueue(image);
2113           if (p == (const PixelPacket *) NULL)
2114             break;
2115           for (x=0; x < (long) GetImageExtent(image); x++)
2116           {
2117             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2118             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2119             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2120             *q++=ScaleQuantumToLong((Quantum) (GetAlphaPixelComponent(p)));
2121             p++;
2122           }
2123           break;
2124         }
2125       if (LocaleCompare(stream_info->map,"BGRP") == 0)
2126         {
2127           p=GetAuthenticPixelQueue(image);
2128           if (p == (const PixelPacket *) NULL)
2129             break;
2130           for (x=0; x < (long) GetImageExtent(image); x++)
2131           {
2132             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2133             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2134             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2135             *q++=0;
2136             p++;
2137           }
2138           break;
2139         }
2140       if (LocaleCompare(stream_info->map,"I") == 0)
2141         {
2142           p=GetAuthenticPixelQueue(image);
2143           if (p == (const PixelPacket *) NULL)
2144             break;
2145           for (x=0; x < (long) GetImageExtent(image); x++)
2146           {
2147             *q++=ScaleQuantumToLong(PixelIntensityToQuantum(p));
2148             p++;
2149           }
2150           break;
2151         }
2152       if (LocaleCompare(stream_info->map,"RGB") == 0)
2153         {
2154           p=GetAuthenticPixelQueue(image);
2155           if (p == (const PixelPacket *) NULL)
2156             break;
2157           for (x=0; x < (long) GetImageExtent(image); x++)
2158           {
2159             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2160             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2161             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2162             p++;
2163           }
2164           break;
2165         }
2166       if (LocaleCompare(stream_info->map,"RGBA") == 0)
2167         {
2168           p=GetAuthenticPixelQueue(image);
2169           if (p == (const PixelPacket *) NULL)
2170             break;
2171           for (x=0; x < (long) GetImageExtent(image); x++)
2172           {
2173             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2174             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2175             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2176             *q++=ScaleQuantumToLong((Quantum) (GetAlphaPixelComponent(p)));
2177             p++;
2178           }
2179           break;
2180         }
2181       if (LocaleCompare(stream_info->map,"RGBP") == 0)
2182         {
2183           p=GetAuthenticPixelQueue(image);
2184           if (p == (const PixelPacket *) NULL)
2185             break;
2186           for (x=0; x < (long) GetImageExtent(image); x++)
2187           {
2188             *q++=ScaleQuantumToLong(GetRedPixelComponent(p));
2189             *q++=ScaleQuantumToLong(GetGreenPixelComponent(p));
2190             *q++=ScaleQuantumToLong(GetBluePixelComponent(p));
2191             *q++=0;
2192             p++;
2193           }
2194           break;
2195         }
2196       p=GetAuthenticPixelQueue(image);
2197       if (p == (const PixelPacket *) NULL)
2198         break;
2199       indexes=GetAuthenticIndexQueue(image);
2200       for (x=0; x < (long) GetImageExtent(image); x++)
2201       {
2202         for (i=0; i < (long) length; i++)
2203         {
2204           *q=0;
2205           switch (quantum_map[i])
2206           {
2207             case RedQuantum:
2208             case CyanQuantum:
2209             {
2210               *q=ScaleQuantumToLong(GetRedPixelComponent(p));
2211               break;
2212             }
2213             case GreenQuantum:
2214             case MagentaQuantum:
2215             {
2216               *q=ScaleQuantumToLong(GetGreenPixelComponent(p));
2217               break;
2218             }
2219             case BlueQuantum:
2220             case YellowQuantum:
2221             {
2222               *q=ScaleQuantumToLong(GetBluePixelComponent(p));
2223               break;
2224             }
2225             case AlphaQuantum:
2226             {
2227               *q=ScaleQuantumToLong((Quantum) (GetAlphaPixelComponent(p)));
2228               break;
2229             }
2230             case OpacityQuantum:
2231             {
2232               *q=ScaleQuantumToLong(GetOpacityPixelComponent(p));
2233               break;
2234             }
2235             case BlackQuantum:
2236             {
2237               if (image->colorspace == CMYKColorspace)
2238                 *q=ScaleQuantumToLong(indexes[x]);
2239               break;
2240             }
2241             case IndexQuantum:
2242             {
2243               *q=ScaleQuantumToLong(PixelIntensityToQuantum(p));
2244               break;
2245             }
2246             default:
2247               break;
2248           }
2249           q++;
2250         }
2251         p++;
2252       }
2253       break;
2254     }
2255     case QuantumPixel:
2256     {
2257       register Quantum
2258         *q;
2259
2260       q=(Quantum *) stream_info->pixels;
2261       if (LocaleCompare(stream_info->map,"BGR") == 0)
2262         {
2263           p=GetAuthenticPixelQueue(image);
2264           if (p == (const PixelPacket *) NULL)
2265             break;
2266           for (x=0; x < (long) GetImageExtent(image); x++)
2267           {
2268             *q++=GetBluePixelComponent(p);
2269             *q++=GetGreenPixelComponent(p);
2270             *q++=GetRedPixelComponent(p);
2271             p++;
2272           }
2273           break;
2274         }
2275       if (LocaleCompare(stream_info->map,"BGRA") == 0)
2276         {
2277           p=GetAuthenticPixelQueue(image);
2278           if (p == (const PixelPacket *) NULL)
2279             break;
2280           for (x=0; x < (long) GetImageExtent(image); x++)
2281           {
2282             *q++=GetBluePixelComponent(p);
2283             *q++=GetGreenPixelComponent(p);
2284             *q++=GetRedPixelComponent(p);
2285             *q++=(Quantum) (GetAlphaPixelComponent(p));
2286             p++;
2287           }
2288           break;
2289         }
2290       if (LocaleCompare(stream_info->map,"BGRP") == 0)
2291         {
2292           p=GetAuthenticPixelQueue(image);
2293           if (p == (const PixelPacket *) NULL)
2294             break;
2295           for (x=0; x < (long) GetImageExtent(image); x++)
2296           {
2297             *q++=GetBluePixelComponent(p);
2298             *q++=GetGreenPixelComponent(p);
2299             *q++=GetRedPixelComponent(p);
2300             *q++=0;
2301             p++;
2302           }
2303           break;
2304         }
2305       if (LocaleCompare(stream_info->map,"I") == 0)
2306         {
2307           p=GetAuthenticPixelQueue(image);
2308           if (p == (const PixelPacket *) NULL)
2309             break;
2310           for (x=0; x < (long) GetImageExtent(image); x++)
2311           {
2312             *q++=PixelIntensityToQuantum(p);
2313             p++;
2314           }
2315           break;
2316         }
2317       if (LocaleCompare(stream_info->map,"RGB") == 0)
2318         {
2319           p=GetAuthenticPixelQueue(image);
2320           if (p == (const PixelPacket *) NULL)
2321             break;
2322           for (x=0; x < (long) GetImageExtent(image); x++)
2323           {
2324             *q++=GetRedPixelComponent(p);
2325             *q++=GetGreenPixelComponent(p);
2326             *q++=GetBluePixelComponent(p);
2327             p++;
2328           }
2329           break;
2330         }
2331       if (LocaleCompare(stream_info->map,"RGBA") == 0)
2332         {
2333           p=GetAuthenticPixelQueue(image);
2334           if (p == (const PixelPacket *) NULL)
2335             break;
2336           for (x=0; x < (long) GetImageExtent(image); x++)
2337           {
2338             *q++=GetRedPixelComponent(p);
2339             *q++=GetGreenPixelComponent(p);
2340             *q++=GetBluePixelComponent(p);
2341             *q++=(Quantum) (GetAlphaPixelComponent(p));
2342             p++;
2343           }
2344           break;
2345         }
2346       if (LocaleCompare(stream_info->map,"RGBP") == 0)
2347         {
2348           p=GetAuthenticPixelQueue(image);
2349           if (p == (const PixelPacket *) NULL)
2350             break;
2351           for (x=0; x < (long) GetImageExtent(image); x++)
2352           {
2353             *q++=GetRedPixelComponent(p);
2354             *q++=GetGreenPixelComponent(p);
2355             *q++=GetBluePixelComponent(p);
2356             *q++=0U;
2357             p++;
2358           }
2359           break;
2360         }
2361       p=GetAuthenticPixelQueue(image);
2362       if (p == (const PixelPacket *) NULL)
2363         break;
2364       indexes=GetAuthenticIndexQueue(image);
2365       for (x=0; x < (long) GetImageExtent(image); x++)
2366       {
2367         for (i=0; i < (long) length; i++)
2368         {
2369           *q=(Quantum) 0;
2370           switch (quantum_map[i])
2371           {
2372             case RedQuantum:
2373             case CyanQuantum:
2374             {
2375               *q=GetRedPixelComponent(p);
2376               break;
2377             }
2378             case GreenQuantum:
2379             case MagentaQuantum:
2380             {
2381               *q=GetGreenPixelComponent(p);
2382               break;
2383             }
2384             case BlueQuantum:
2385             case YellowQuantum:
2386             {
2387               *q=GetBluePixelComponent(p);
2388               break;
2389             }
2390             case AlphaQuantum:
2391             {
2392               *q=(Quantum) (GetAlphaPixelComponent(p));
2393               break;
2394             }
2395             case OpacityQuantum:
2396             {
2397               *q=GetOpacityPixelComponent(p);
2398               break;
2399             }
2400             case BlackQuantum:
2401             {
2402               if (image->colorspace == CMYKColorspace)
2403                 *q=indexes[x];
2404               break;
2405             }
2406             case IndexQuantum:
2407             {
2408               *q=(PixelIntensityToQuantum(p));
2409               break;
2410             }
2411             default:
2412               *q=0;
2413           }
2414           q++;
2415         }
2416         p++;
2417       }
2418       break;
2419     }
2420     case ShortPixel:
2421     {
2422       register unsigned short
2423         *q;
2424
2425       q=(unsigned short *) stream_info->pixels;
2426       if (LocaleCompare(stream_info->map,"BGR") == 0)
2427         {
2428           p=GetAuthenticPixelQueue(image);
2429           if (p == (const PixelPacket *) NULL)
2430             break;
2431           for (x=0; x < (long) GetImageExtent(image); x++)
2432           {
2433             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2434             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2435             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2436             p++;
2437           }
2438           break;
2439         }
2440       if (LocaleCompare(stream_info->map,"BGRA") == 0)
2441         {
2442           p=GetAuthenticPixelQueue(image);
2443           if (p == (const PixelPacket *) NULL)
2444             break;
2445           for (x=0; x < (long) GetImageExtent(image); x++)
2446           {
2447             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2448             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2449             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2450             *q++=ScaleQuantumToShort((Quantum) (GetAlphaPixelComponent(p)));
2451             p++;
2452           }
2453           break;
2454         }
2455       if (LocaleCompare(stream_info->map,"BGRP") == 0)
2456         {
2457           p=GetAuthenticPixelQueue(image);
2458             if (p == (const PixelPacket *) NULL)
2459             break;
2460           for (x=0; x < (long) GetImageExtent(image); x++)
2461           {
2462             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2463             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2464             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2465             *q++=0;
2466             p++;
2467           }
2468           break;
2469         }
2470       if (LocaleCompare(stream_info->map,"I") == 0)
2471         {
2472           p=GetAuthenticPixelQueue(image);
2473           if (p == (const PixelPacket *) NULL)
2474             break;
2475           for (x=0; x < (long) GetImageExtent(image); x++)
2476           {
2477             *q++=ScaleQuantumToShort(PixelIntensityToQuantum(p));
2478             p++;
2479           }
2480           break;
2481         }
2482       if (LocaleCompare(stream_info->map,"RGB") == 0)
2483         {
2484           p=GetAuthenticPixelQueue(image);
2485           if (p == (const PixelPacket *) NULL)
2486             break;
2487           for (x=0; x < (long) GetImageExtent(image); x++)
2488           {
2489             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2490             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2491             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2492             p++;
2493           }
2494           break;
2495         }
2496       if (LocaleCompare(stream_info->map,"RGBA") == 0)
2497         {
2498           p=GetAuthenticPixelQueue(image);
2499           if (p == (const PixelPacket *) NULL)
2500             break;
2501           for (x=0; x < (long) GetImageExtent(image); x++)
2502           {
2503             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2504             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2505             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2506             *q++=ScaleQuantumToShort((Quantum) (GetAlphaPixelComponent(p)));
2507             p++;
2508           }
2509           break;
2510         }
2511       if (LocaleCompare(stream_info->map,"RGBP") == 0)
2512         {
2513           p=GetAuthenticPixelQueue(image);
2514           if (p == (const PixelPacket *) NULL)
2515             break;
2516           for (x=0; x < (long) GetImageExtent(image); x++)
2517           {
2518             *q++=ScaleQuantumToShort(GetRedPixelComponent(p));
2519             *q++=ScaleQuantumToShort(GetGreenPixelComponent(p));
2520             *q++=ScaleQuantumToShort(GetBluePixelComponent(p));
2521             *q++=0;
2522             p++;
2523           }
2524           break;
2525         }
2526       p=GetAuthenticPixelQueue(image);
2527       if (p == (const PixelPacket *) NULL)
2528         break;
2529       indexes=GetAuthenticIndexQueue(image);
2530       for (x=0; x < (long) GetImageExtent(image); x++)
2531       {
2532         for (i=0; i < (long) length; i++)
2533         {
2534           *q=0;
2535           switch (quantum_map[i])
2536           {
2537             case RedQuantum:
2538             case CyanQuantum:
2539             {
2540               *q=ScaleQuantumToShort(GetRedPixelComponent(p));
2541               break;
2542             }
2543             case GreenQuantum:
2544             case MagentaQuantum:
2545             {
2546               *q=ScaleQuantumToShort(GetGreenPixelComponent(p));
2547               break;
2548             }
2549             case BlueQuantum:
2550             case YellowQuantum:
2551             {
2552               *q=ScaleQuantumToShort(GetBluePixelComponent(p));
2553               break;
2554             }
2555             case AlphaQuantum:
2556             {
2557               *q=ScaleQuantumToShort((Quantum) (GetAlphaPixelComponent(p)));
2558               break;
2559             }
2560             case OpacityQuantum:
2561             {
2562               *q=ScaleQuantumToShort(GetOpacityPixelComponent(p));
2563               break;
2564             }
2565             case BlackQuantum:
2566             {
2567               if (image->colorspace == CMYKColorspace)
2568                 *q=ScaleQuantumToShort(indexes[x]);
2569               break;
2570             }
2571             case IndexQuantum:
2572             {
2573               *q=ScaleQuantumToShort(PixelIntensityToQuantum(p));
2574               break;
2575             }
2576             default:
2577               break;
2578           }
2579           q++;
2580         }
2581         p++;
2582       }
2583       break;
2584     }
2585     default:
2586     {
2587       quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
2588       (void) ThrowMagickException(exception,GetMagickModule(),OptionError,
2589         "UnrecognizedPixelMap","`%s'",stream_info->map);
2590       break;
2591     }
2592   }
2593   quantum_map=(QuantumType *) RelinquishMagickMemory(quantum_map);
2594   return(MagickTrue);
2595 }
2596 \f
2597 /*
2598 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2599 %                                                                             %
2600 %                                                                             %
2601 %                                                                             %
2602 +   S y n c A u t h e n t i c P i x e l s S t r e a m                         %
2603 %                                                                             %
2604 %                                                                             %
2605 %                                                                             %
2606 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2607 %
2608 %  SyncAuthenticPixelsStream() calls the user supplied callback method with
2609 %  the latest stream of pixels.
2610 %
2611 %  The format of the SyncAuthenticPixelsStream method is:
2612 %
2613 %      MagickBooleanType SyncAuthenticPixelsStream(Image *image,
2614 %        ExceptionInfo *exception)
2615 %
2616 %  A description of each parameter follows:
2617 %
2618 %    o image: the image.
2619 %
2620 %    o exception: return any errors or warnings in this structure.
2621 %
2622 */
2623 static MagickBooleanType SyncAuthenticPixelsStream(Image *image,
2624   ExceptionInfo *exception)
2625 {
2626   CacheInfo
2627     *cache_info;
2628
2629   size_t
2630     length;
2631
2632   StreamHandler
2633     stream_handler;
2634
2635   assert(image != (Image *) NULL);
2636   assert(image->signature == MagickSignature);
2637   if (image->debug != MagickFalse)
2638     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2639   cache_info=(CacheInfo *) image->cache;
2640   assert(cache_info->signature == MagickSignature);
2641   stream_handler=GetBlobStreamHandler(image);
2642   if (stream_handler == (StreamHandler) NULL)
2643     {
2644       (void) ThrowMagickException(exception,GetMagickModule(),StreamError,
2645         "NoStreamHandlerIsDefined","`%s'",image->filename);
2646       return(MagickFalse);
2647     }
2648   length=stream_handler(image,cache_info->pixels,(size_t) cache_info->columns);
2649   return(length == cache_info->columns ? MagickTrue : MagickFalse);
2650 }
2651 \f
2652 /*
2653 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2654 %                                                                             %
2655 %                                                                             %
2656 %                                                                             %
2657 %   W r i t e S t r e a m                                                     %
2658 %                                                                             %
2659 %                                                                             %
2660 %                                                                             %
2661 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2662 %
2663 %  WriteStream() makes the image pixels available to a user supplied callback
2664 %  method immediately upon writing pixel data with the WriteImage() method.
2665 %
2666 %  The format of the WriteStream() method is:
2667 %
2668 %      MagickBooleanType WriteStream(const ImageInfo *image_info,Image *,
2669 %        StreamHandler stream)
2670 %
2671 %  A description of each parameter follows:
2672 %
2673 %    o image_info: the image info.
2674 %
2675 %    o stream: A callback method.
2676 %
2677 */
2678 MagickExport MagickBooleanType WriteStream(const ImageInfo *image_info,
2679   Image *image,StreamHandler stream)
2680 {
2681   ImageInfo
2682     *write_info;
2683
2684   MagickBooleanType
2685     status;
2686
2687   assert(image_info != (ImageInfo *) NULL);
2688   assert(image_info->signature == MagickSignature);
2689   if (image_info->debug != MagickFalse)
2690     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
2691       image_info->filename);
2692   assert(image != (Image *) NULL);
2693   assert(image->signature == MagickSignature);
2694   write_info=CloneImageInfo(image_info);
2695   write_info->stream=stream;
2696   status=WriteImage(write_info,image);
2697   write_info=DestroyImageInfo(write_info);
2698   return(status);
2699 }