2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6 % M M AAA GGGG IIIII CCCC K K %
7 % MM MM A A G I C K K %
8 % M M M AAAAA G GGG I C KKK %
9 % M M A A G G I C K K %
10 % M M A A GGGG IIIII CCCC K K %
13 % Methods to Read or List ImageMagick Image formats %
21 % Copyright 1999-2009 ImageMagick Studio LLC, a non-profit organization %
22 % dedicated to making software imaging solutions freely available. %
24 % You may not use this file except in compliance with the License. You may %
25 % obtain a copy of the License at %
27 % http://www.imagemagick.org/script/license.php %
29 % Unless required by applicable law or agreed to in writing, software %
30 % distributed under the License is distributed on an "AS IS" BASIS, %
31 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
32 % See the License for the specific language governing permissions and %
33 % limitations under the License. %
35 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
43 #include "magick/studio.h"
44 #include "magick/blob.h"
45 #include "magick/cache.h"
46 #include "magick/coder.h"
47 #include "magick/client.h"
48 #include "magick/coder.h"
49 #include "magick/configure.h"
50 #include "magick/constitute.h"
51 #include "magick/delegate.h"
52 #include "magick/draw.h"
53 #include "magick/exception.h"
54 #include "magick/exception-private.h"
55 #include "magick/locale_.h"
56 #include "magick/log.h"
57 #include "magick/magic.h"
58 #include "magick/magick.h"
59 #include "magick/memory_.h"
60 #include "magick/mime.h"
61 #include "magick/module.h"
62 #if defined(__WINDOWS__)
63 # include "magick/nt-feature.h"
65 #include "magick/random_.h"
66 #include "magick/registry.h"
67 #include "magick/resource_.h"
68 #include "magick/policy.h"
69 #include "magick/semaphore.h"
70 #include "magick/signature-private.h"
71 #include "magick/splay-tree.h"
72 #include "magick/string_.h"
73 #include "magick/thread_.h"
74 #include "magick/thread-private.h"
75 #include "magick/token.h"
76 #include "magick/utility.h"
77 #include "magick/xwindow-private.h"
82 #if !defined(MAGICKCORE_RETSIGTYPE)
83 # define MAGICKCORE_RETSIGTYPE void
86 # define SIG_DFL ((SignalHandler *) 0)
89 # define SIG_ERR ((SignalHandler *) -1)
98 typedef MAGICKCORE_RETSIGTYPE
105 *magick_semaphore = (SemaphoreInfo *) NULL;
108 *signal_handlers[SIGMAX] = { (SignalHandler *) NULL };
111 *magick_list = (SplayTreeInfo *) NULL;
113 static volatile MagickBooleanType
114 instantiate_magick = MagickFalse; /* double-checked locking pattern */
117 Forward declarations.
119 static MagickBooleanType
120 InitializeMagickList(ExceptionInfo *);
123 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
127 + G e t I m a g e D e c o d e r %
131 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
133 % GetImageDecoder() returns the image decoder.
135 % The format of the GetImageDecoder method is:
137 % DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
139 % A description of each parameter follows:
141 % o magick_info: The magick info.
144 MagickExport DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
146 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
147 assert(magick_info != (MagickInfo *) NULL);
148 assert(magick_info->signature == MagickSignature);
149 return(magick_info->decoder);
153 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
157 + G e t I m a g e E n c o d e r %
161 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
163 % GetImageEncoder() returns the image encoder.
165 % The format of the GetImageEncoder method is:
167 % EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
169 % A description of each parameter follows:
171 % o magick_info: The magick info.
174 MagickExport EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
176 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
177 assert(magick_info != (MagickInfo *) NULL);
178 assert(magick_info->signature == MagickSignature);
179 return(magick_info->encoder);
183 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
187 + G e t I m a g e M a g i c k %
191 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
193 % GetImageMagick() searches for an image format that matches the specified
194 % magick string. If one is found, MagickTrue is returned otherwise
197 % The format of the GetImageMagick method is:
199 % MagickBooleanType GetImageMagick(const unsigned char *magick,
200 % const size_t length,char *format)
202 % A description of each parameter follows:
204 % o magick: the image format we are searching for.
206 % o length: the length of the binary string.
208 % o format: the image format as determined by the magick bytes.
211 MagickExport MagickBooleanType GetImageMagick(const unsigned char *magick,
212 const size_t length,char *format)
220 register const MagickInfo
223 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
224 assert(magick != (const unsigned char *) NULL);
225 exception=AcquireExceptionInfo();
226 p=GetMagickInfo("*",exception);
227 exception=DestroyExceptionInfo(exception);
228 if (p == (const MagickInfo *) NULL)
231 LockSemaphoreInfo(magick_semaphore);
232 ResetSplayTreeIterator(magick_list);
233 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
234 while (p != (const MagickInfo *) NULL)
236 if ((p->magick != (IsImageFormatHandler *) NULL) &&
237 (p->magick(magick,length) != 0))
240 (void) CopyMagickString(format,p->name,MaxTextExtent);
243 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
245 UnlockSemaphoreInfo(magick_semaphore);
250 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
254 + G e t M a g i c k A d j o i n %
258 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
260 % GetMagickAdjoin() returns MagickTrue if the magick adjoin is MagickTrue.
262 % The format of the GetMagickAdjoin method is:
264 % MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
266 % A description of each parameter follows:
268 % o magick_info: The magick info.
271 MagickExport MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
273 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
274 assert(magick_info != (MagickInfo *) NULL);
275 assert(magick_info->signature == MagickSignature);
276 return(magick_info->adjoin);
280 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
284 + G e t M a g i c k B l o b S u p p o r t %
288 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
290 % GetMagickBlobSupport() returns MagickTrue if the magick supports blobs.
292 % The format of the GetMagickBlobSupport method is:
294 % MagickBooleanType GetMagickBlobSupport(const MagickInfo *magick_info)
296 % A description of each parameter follows:
298 % o magick_info: The magick info.
301 MagickExport MagickBooleanType GetMagickBlobSupport(
302 const MagickInfo *magick_info)
304 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
305 assert(magick_info != (MagickInfo *) NULL);
306 assert(magick_info->signature == MagickSignature);
307 return(magick_info->blob_support);
311 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
315 + G e t M a g i c k D e s c r i p t i o n %
319 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
321 % GetMagickDescription() returns the magick description.
323 % The format of the GetMagickDescription method is:
325 % const char *GetMagickDescription(const MagickInfo *magick_info)
327 % A description of each parameter follows:
329 % o magick_info: The magick info.
332 MagickExport const char *GetMagickDescription(const MagickInfo *magick_info)
334 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
335 assert(magick_info != (MagickInfo *) NULL);
336 assert(magick_info->signature == MagickSignature);
337 return(magick_info->description);
341 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
345 + G e t M a g i c k E n d i a n S u p p o r t %
349 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
351 % GetMagickEndianSupport() returns the MagickTrue if the coder respects
352 % endianness other than MSBEndian.
354 % The format of the GetMagickEndianSupport method is:
356 % MagickBooleanType GetMagickEndianSupport(const MagickInfo *magick_info)
358 % A description of each parameter follows:
360 % o magick_info: The magick info.
363 MagickExport MagickBooleanType GetMagickEndianSupport(
364 const MagickInfo *magick_info)
366 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
367 assert(magick_info != (MagickInfo *) NULL);
368 assert(magick_info->signature == MagickSignature);
369 return(magick_info->endian_support);
373 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
377 + G e t M a g i c k I n f o %
381 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
383 % GetMagickInfo() returns a pointer MagickInfo structure that matches
384 % the specified name. If name is NULL, the head of the image format list
387 % The format of the GetMagickInfo method is:
389 % const MagickInfo *GetMagickInfo(const char *name,Exception *exception)
391 % A description of each parameter follows:
393 % o name: the image format we are looking for.
395 % o exception: return any errors or warnings in this structure.
398 MagickExport const MagickInfo *GetMagickInfo(const char *name,
399 ExceptionInfo *exception)
401 register const MagickInfo
404 assert(exception != (ExceptionInfo *) NULL);
405 if ((magick_list == (SplayTreeInfo *) NULL) ||
406 (instantiate_magick == MagickFalse))
407 if (InitializeMagickList(exception) == MagickFalse)
408 return((const MagickInfo *) NULL);
409 if ((name == (const char *) NULL) || (LocaleCompare(name,"*") == 0))
411 #if defined(MAGICKCORE_MODULES_SUPPORT)
412 if (LocaleCompare(name,"*") == 0)
413 (void) OpenModules(exception);
415 LockSemaphoreInfo(magick_semaphore);
416 ResetSplayTreeIterator(magick_list);
417 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
418 UnlockSemaphoreInfo(magick_semaphore);
424 LockSemaphoreInfo(magick_semaphore);
425 ResetSplayTreeIterator(magick_list);
426 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
427 while (p != (const MagickInfo *) NULL)
429 if (LocaleCompare(p->name,name) == 0)
431 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
433 #if defined(MAGICKCORE_MODULES_SUPPORT)
434 if (p == (const MagickInfo *) NULL)
437 (void) OpenModule(name,exception);
438 ResetSplayTreeIterator(magick_list);
439 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
440 while (p != (const MagickInfo *) NULL)
442 if (LocaleCompare(p->name,name) == 0)
444 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
448 UnlockSemaphoreInfo(magick_semaphore);
453 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
457 + G e t M a g i c k I n f o L i s t %
461 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
463 % GetMagickInfoList() returns any image formats that match the specified
466 % The format of the GetMagickInfoList function is:
468 % const MagickInfo **GetMagickInfoList(const char *pattern,
469 % unsigned long *number_formats,ExceptionInfo *exception)
471 % A description of each parameter follows:
473 % o pattern: Specifies a pointer to a text string containing a pattern.
475 % o number_formats: This integer returns the number of formats in the list.
477 % o exception: return any errors or warnings in this structure.
481 #if defined(__cplusplus) || defined(c_plusplus)
485 static int MagickInfoCompare(const void *x,const void *y)
491 p=(const MagickInfo **) x,
492 q=(const MagickInfo **) y;
493 return(LocaleCompare((*p)->name,(*q)->name));
496 #if defined(__cplusplus) || defined(c_plusplus)
500 MagickExport const MagickInfo **GetMagickInfoList(const char *pattern,
501 unsigned long *number_formats,ExceptionInfo *exception)
506 register const MagickInfo
513 Allocate magick list.
515 assert(pattern != (char *) NULL);
516 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
517 assert(number_formats != (unsigned long *) NULL);
519 p=GetMagickInfo("*",exception);
520 if (p == (const MagickInfo *) NULL)
521 return((const MagickInfo **) NULL);
522 formats=(const MagickInfo **) AcquireQuantumMemory((size_t)
523 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
524 if (formats == (const MagickInfo **) NULL)
525 return((const MagickInfo **) NULL);
527 Generate magick list.
529 LockSemaphoreInfo(magick_semaphore);
530 ResetSplayTreeIterator(magick_list);
531 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
532 for (i=0; p != (const MagickInfo *) NULL; )
534 if ((p->stealth == MagickFalse) &&
535 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
537 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
539 UnlockSemaphoreInfo(magick_semaphore);
540 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickInfoCompare);
541 formats[i]=(MagickInfo *) NULL;
542 *number_formats=(unsigned long) i;
547 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
551 + G e t M a g i c k L i s t %
555 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
557 % GetMagickList() returns any image formats that match the specified pattern.
559 % The format of the GetMagickList function is:
561 % char **GetMagickList(const char *pattern,unsigned long *number_formats,
562 % ExceptionInfo *exception)
564 % A description of each parameter follows:
566 % o pattern: Specifies a pointer to a text string containing a pattern.
568 % o number_formats: This integer returns the number of formats in the list.
570 % o exception: return any errors or warnings in this structure.
574 #if defined(__cplusplus) || defined(c_plusplus)
578 static int MagickCompare(const void *x,const void *y)
586 return(LocaleCompare(*p,*q));
589 #if defined(__cplusplus) || defined(c_plusplus)
593 MagickExport char **GetMagickList(const char *pattern,
594 unsigned long *number_formats,ExceptionInfo *exception)
599 register const MagickInfo
606 Allocate magick list.
608 assert(pattern != (char *) NULL);
609 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
610 assert(number_formats != (unsigned long *) NULL);
612 p=GetMagickInfo("*",exception);
613 if (p == (const MagickInfo *) NULL)
614 return((char **) NULL);
615 formats=(char **) AcquireQuantumMemory((size_t)
616 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
617 if (formats == (char **) NULL)
618 return((char **) NULL);
619 LockSemaphoreInfo(magick_semaphore);
620 ResetSplayTreeIterator(magick_list);
621 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
622 for (i=0; p != (const MagickInfo *) NULL; )
624 if ((p->stealth == MagickFalse) &&
625 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
626 formats[i++]=ConstantString(p->name);
627 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
629 UnlockSemaphoreInfo(magick_semaphore);
630 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickCompare);
631 formats[i]=(char *) NULL;
632 *number_formats=(unsigned long) i;
637 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
641 + G e t M a g i c k E n d i a n S u p p o r t %
645 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
647 % GetMagickRawSupport() returns the MagickTrue if the coder is a raw format.
649 % The format of the GetMagickRawSupport method is:
651 % MagickBooleanType GetMagickRawSupport(const MagickInfo *magick_info)
653 % A description of each parameter follows:
655 % o magick_info: The magick info.
658 MagickExport MagickBooleanType GetMagickRawSupport(
659 const MagickInfo *magick_info)
661 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
662 assert(magick_info != (MagickInfo *) NULL);
663 assert(magick_info->signature == MagickSignature);
664 return(magick_info->raw);
668 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
672 + G e t M a g i c k S e e k a b l e S t r e a m %
676 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
678 % GetMagickSeekableStream() returns MagickTrue if the magick supports a
681 % The format of the GetMagickSeekableStream method is:
683 % MagickBooleanType GetMagickSeekableStream(const MagickInfo *magick_info)
685 % A description of each parameter follows:
687 % o magick_info: The magick info.
690 MagickExport MagickBooleanType GetMagickSeekableStream(
691 const MagickInfo *magick_info)
693 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
694 assert(magick_info != (MagickInfo *) NULL);
695 assert(magick_info->signature == MagickSignature);
696 return(magick_info->seekable_stream);
700 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
704 + G e t M a g i c k T h r e a d S u p p o r t %
708 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
710 % GetMagickThreadSupport() returns MagickTrue if the magick supports threads.
712 % The format of the GetMagickThreadSupport method is:
714 % MagickStatusType GetMagickThreadSupport(const MagickInfo *magick_info)
716 % A description of each parameter follows:
718 % o magick_info: The magick info.
721 MagickExport MagickStatusType GetMagickThreadSupport(
722 const MagickInfo *magick_info)
724 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
725 assert(magick_info != (MagickInfo *) NULL);
726 assert(magick_info->signature == MagickSignature);
727 return(magick_info->thread_support);
731 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
735 + I n i t i a l i z e M a g i c k L i s t %
739 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
741 % InitializeMagickList() initializes the magick list.
743 % The format of the InitializeMagickList() method is:
745 % InitializeMagickList(Exceptioninfo *exception)
747 % A description of each parameter follows.
749 % o exception: return any errors or warnings in this structure.
753 static void *DestroyMagickNode(void *magick_info)
758 p=(MagickInfo *) magick_info;
759 if (p->name != (char *) NULL)
760 p->name=DestroyString(p->name);
761 if (p->description != (char *) NULL)
762 p->description=DestroyString(p->description);
763 if (p->version != (char *) NULL)
764 p->version=DestroyString(p->version);
765 if (p->note != (char *) NULL)
766 p->note=DestroyString(p->note);
767 if (p->module != (char *) NULL)
768 p->module=DestroyString(p->module);
769 return(RelinquishMagickMemory(p));
772 static MagickBooleanType InitializeMagickList(ExceptionInfo *exception)
775 if ((magick_list == (SplayTreeInfo *) NULL) &&
776 (instantiate_magick == MagickFalse))
778 if (magick_semaphore == (SemaphoreInfo *) NULL)
779 AcquireSemaphoreInfo(&magick_semaphore);
780 LockSemaphoreInfo(magick_semaphore);
781 if ((magick_list == (SplayTreeInfo *) NULL) &&
782 (instantiate_magick == MagickFalse))
790 magick_list=NewSplayTree(CompareSplayTreeString,
791 (void *(*)(void *)) NULL,DestroyMagickNode);
792 if (magick_list == (SplayTreeInfo *) NULL)
793 ThrowFatalException(ResourceLimitFatalError,
794 "MemoryAllocationFailed");
795 magick_info=SetMagickInfo("ephemeral");
796 magick_info->stealth=MagickTrue;
797 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
798 if (status == MagickFalse)
799 ThrowFatalException(ResourceLimitFatalError,
800 "MemoryAllocationFailed");
801 magick_info=SetMagickInfo("clipmask");
802 magick_info->stealth=MagickTrue;
803 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
804 if (status == MagickFalse)
809 message=GetExceptionMessage(errno);
810 ThrowFatalException(ResourceLimitFatalError,
811 "MemoryAllocationFailed");
812 message=DestroyString(message);
814 #if defined(MAGICKCORE_MODULES_SUPPORT)
815 (void) GetModuleInfo((char *) NULL,exception);
817 #if !defined(MAGICKCORE_BUILD_MODULES)
818 RegisterStaticModules();
820 instantiate_magick=MagickTrue;
822 UnlockSemaphoreInfo(magick_semaphore);
824 return(magick_list != (SplayTreeInfo *) NULL ? MagickTrue : MagickFalse);
828 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
832 + I s M a g i c k C o n f l i c t %
836 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
838 % IsMagickConflict() returns MagickTrue if the image format is not a valid
839 % image format or conflicts with a logical drive (.e.g. X:).
841 % The format of the IsMagickConflict method is:
843 % MagickBooleanType IsMagickConflict(const char *magick)
845 % A description of each parameter follows:
847 % o magick: Specifies the image format.
850 MagickExport MagickBooleanType IsMagickConflict(const char *magick)
861 assert(magick != (char *) NULL);
862 exception=AcquireExceptionInfo();
863 magick_info=GetMagickInfo(magick,exception);
864 delegate_info=GetDelegateInfo(magick,(char *) NULL,exception);
865 if (delegate_info == (const DelegateInfo *) NULL)
866 delegate_info=GetDelegateInfo((char *) NULL,magick,exception);
867 exception=DestroyExceptionInfo(exception);
868 if ((magick_info == (const MagickInfo *) NULL) &&
869 (delegate_info == (const DelegateInfo *) NULL))
871 #if defined(macintosh)
872 return(MACIsMagickConflict(magick));
874 return(VMSIsMagickConflict(magick));
875 #elif defined(__WINDOWS__)
876 return(NTIsMagickConflict(magick));
883 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
887 + L i s t M a g i c k I n f o %
891 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
893 % ListMagickInfo() lists the image formats to a file.
895 % The format of the ListMagickInfo method is:
897 % MagickBooleanType ListMagickInfo(FILE *file,ExceptionInfo *exception)
899 % A description of each parameter follows.
901 % o file: A file handle.
903 % o exception: return any errors or warnings in this structure.
906 MagickExport MagickBooleanType ListMagickInfo(FILE *file,
907 ExceptionInfo *exception)
921 if (file == (FILE *) NULL)
923 magick_info=GetMagickInfoList("*",&number_formats,exception);
924 if (magick_info == (const MagickInfo **) NULL)
926 ClearMagickException(exception);
927 #if !defined(MAGICKCORE_MODULES_SUPPORT)
928 (void) fprintf(file," Format Mode Description\n");
930 (void) fprintf(file," Format Module Mode Description\n");
932 (void) fprintf(file,"--------------------------------------------------------"
933 "-----------------------\n");
934 for (i=0; i < (long) number_formats; i++)
936 if (magick_info[i]->stealth != MagickFalse)
938 (void) fprintf(file,"%9s%c ",magick_info[i]->name != (char *) NULL ?
939 magick_info[i]->name : "",
940 magick_info[i]->blob_support != MagickFalse ? '*' : ' ');
941 #if defined(MAGICKCORE_MODULES_SUPPORT)
944 module[MaxTextExtent];
947 if (magick_info[i]->module != (char *) NULL)
948 (void) CopyMagickString(module,magick_info[i]->module,MaxTextExtent);
949 (void) ConcatenateMagickString(module," ",MaxTextExtent);
951 (void) fprintf(file,"%9s ",module);
954 (void) fprintf(file,"%c%c%c ",magick_info[i]->decoder ? 'r' : '-',
955 magick_info[i]->encoder ? 'w' : '-',magick_info[i]->encoder != NULL &&
956 magick_info[i]->adjoin != MagickFalse ? '+' : '-');
957 if (magick_info[i]->description != (char *) NULL)
958 (void) fprintf(file," %s",magick_info[i]->description);
959 if (magick_info[i]->version != (char *) NULL)
960 (void) fprintf(file," (%s)",magick_info[i]->version);
961 (void) fprintf(file,"\n");
962 if (magick_info[i]->note != (char *) NULL)
967 text=StringToList(magick_info[i]->note);
968 if (text != (char **) NULL)
970 for (j=0; text[j] != (char *) NULL; j++)
972 (void) fprintf(file," %s\n",text[j]);
973 text[j]=DestroyString(text[j]);
975 text=(char **) RelinquishMagickMemory(text);
979 (void) fprintf(file,"\n* native blob support\n");
980 (void) fprintf(file,"r read support\n");
981 (void) fprintf(file,"w write support\n");
982 (void) fprintf(file,"+ support for multiple images\n");
984 magick_info=(const MagickInfo **) RelinquishMagickMemory((void *)
990 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
994 % I s M a g i c k I n s t a n t i a t e d %
998 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1000 % IsMagickInstantiated() returns MagickTrue if the ImageMagick environment
1001 % is currently instantiated: MagickCoreGenesis() has been called but
1002 % MagickDestroy() has not.
1004 % The format of the IsMagickInstantiated method is:
1006 % MagickBooleanType IsMagickInstantiated(void)
1009 MagickExport MagickBooleanType IsMagickInstantiated(void)
1011 return(instantiate_magick);
1015 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1019 + M a g i c k C o m p o n e n t G e n e s i s %
1023 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1025 % MagickComponentGenesis() instantiates the magick component.
1027 % The format of the MagickComponentGenesis method is:
1029 % MagickBooleanType MagickComponentGenesis(void)
1032 MagickExport MagickBooleanType MagickComponentGenesis(void)
1034 assert(magick_semaphore == (SemaphoreInfo *) NULL);
1035 magick_semaphore=AllocateSemaphoreInfo();
1040 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1044 + M a g i c k C o m p o n e n t T e r m i n u s %
1048 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1050 % MagickComponentTerminus() destroys the magick component.
1052 % The format of the MagickComponentTerminus method is:
1054 % void MagickComponentTerminus(void)
1057 MagickExport void MagickComponentTerminus(void)
1059 if (magick_semaphore == (SemaphoreInfo *) NULL)
1060 AcquireSemaphoreInfo(&magick_semaphore);
1061 LockSemaphoreInfo(magick_semaphore);
1062 if (magick_list != (SplayTreeInfo *) NULL)
1063 magick_list=DestroySplayTree(magick_list);
1064 instantiate_magick=MagickFalse;
1065 UnlockSemaphoreInfo(magick_semaphore);
1066 DestroySemaphoreInfo(&magick_semaphore);
1070 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1074 % M a g i c k C o r e G e n e s i s %
1078 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1080 % MagickCoreGenesis() initializes the MagickCore environment.
1082 % The format of the MagickCoreGenesis function is:
1084 % MagickCoreGenesis(const char *path,
1085 % const MagickBooleanType establish_signal_handlers)
1087 % A description of each parameter follows:
1089 % o path: the execution path of the current ImageMagick client.
1091 % o establish_signal_handlers: set to MagickTrue to use MagickCore's own
1092 % signal handlers for common signals.
1096 static SignalHandler *SetMagickSignalHandler(int signal_number,
1097 SignalHandler *handler)
1099 #if defined(MAGICKCORE_HAVE_SIGACTION) && defined(MAGICKCORE_HAVE_SIGEMPTYSET)
1111 sigaddset(&mask,signal_number);
1112 sigprocmask(SIG_BLOCK,&mask,NULL);
1113 action.sa_mask=mask;
1114 action.sa_handler=handler;
1116 #if defined(SA_INTERRUPT)
1117 action.sa_flags|=SA_INTERRUPT;
1119 status=sigaction(signal_number,&action,&previous_action);
1122 sigprocmask(SIG_UNBLOCK,&mask,NULL);
1123 return(previous_action.sa_handler);
1125 return(signal(signal_number,handler));
1129 static void MagickSignalHandler(int signal_number)
1131 #if !defined(MAGICKCORE_HAVE_SIGACTION)
1132 (void) signal(signal_number,SIG_IGN);
1134 AsynchronousResourceComponentTerminus();
1135 instantiate_magick=MagickFalse;
1136 (void) SetMagickSignalHandler(signal_number,signal_handlers[signal_number]);
1137 #if defined(MAGICKCORE_HAVE_RAISE)
1138 if (signal_handlers[signal_number] != MagickSignalHandler)
1139 raise(signal_number);
1141 #if !defined(MAGICKCORE_HAVE__EXIT)
1142 exit(signal_number);
1145 if (signal_number == SIGHUP)
1146 exit(signal_number);
1148 #if defined(SIGINT) && !defined(__WINDOWS__)
1149 if (signal_number == SIGINT)
1150 exit(signal_number);
1152 #if defined(SIGTERM)
1153 if (signal_number == SIGTERM)
1154 exit(signal_number);
1156 _exit(signal_number);
1160 static SignalHandler *RegisterMagickSignalHandler(int signal_number)
1165 handler=SetMagickSignalHandler(signal_number,MagickSignalHandler);
1166 if (handler == SIG_ERR)
1168 if (handler != SIG_DFL)
1169 handler=SetMagickSignalHandler(signal_number,handler);
1171 (void) LogMagickEvent(ConfigureEvent,GetMagickModule(),
1172 "Register handler for signal: %d",signal_number);
1176 MagickExport void MagickCoreGenesis(const char *path,
1177 const MagickBooleanType establish_signal_handlers)
1181 execution_path[MaxTextExtent],
1182 filename[MaxTextExtent];
1185 Initialize the Magick environment.
1187 (void) setlocale(LC_ALL,"");
1188 (void) setlocale(LC_NUMERIC,"C");
1189 (void) SemaphoreComponentGenesis();
1190 (void) LogComponentGenesis();
1191 (void) LocaleComponentGenesis();
1192 (void) RandomComponentGenesis();
1193 events=GetEnvironmentValue("MAGICK_DEBUG");
1194 if (events != (char *) NULL)
1196 (void) SetLogEventMask(events);
1197 events=DestroyString(events);
1199 #if defined(__WINDOWS__)
1200 #if defined(_DEBUG) && !defined(__BORLANDC__) && !defined(__MINGW32__)
1201 if (IsEventLogging() != MagickFalse)
1206 debug=_CrtSetDbgFlag(_CRTDBG_REPORT_FLAG);
1207 debug|=_CRTDBG_CHECK_ALWAYS_DF |_CRTDBG_DELAY_FREE_MEM_DF |
1208 _CRTDBG_LEAK_CHECK_DF;
1211 debug=_CrtSetDbgFlag(debug);
1212 _ASSERTE(_CrtCheckMemory());
1218 Set client name and execution path.
1220 (void) GetExecutionPath(execution_path,MaxTextExtent);
1221 if ((path != (const char *) NULL) && (*path != '\0'))
1222 (void) CopyMagickString(execution_path,path,MaxTextExtent);
1223 GetPathComponent(execution_path,TailPath,filename);
1224 (void) SetClientName(filename);
1225 GetPathComponent(execution_path,HeadPath,execution_path);
1226 (void) SetClientPath(execution_path);
1227 if (establish_signal_handlers != MagickFalse)
1230 Set signal handlers.
1232 #if defined(SIGABRT)
1233 if (signal_handlers[SIGABRT] == (SignalHandler *) NULL)
1234 signal_handlers[SIGABRT]=RegisterMagickSignalHandler(SIGABRT);
1237 if (signal_handlers[SIGFPE] == (SignalHandler *) NULL)
1238 signal_handlers[SIGFPE]=RegisterMagickSignalHandler(SIGFPE);
1241 if (signal_handlers[SIGHUP] == (SignalHandler *) NULL)
1242 signal_handlers[SIGHUP]=RegisterMagickSignalHandler(SIGHUP);
1244 #if defined(SIGINT) && !defined(__WINDOWS__)
1245 if (signal_handlers[SIGINT] == (SignalHandler *) NULL)
1246 signal_handlers[SIGINT]=RegisterMagickSignalHandler(SIGINT);
1248 #if defined(SIGQUIT)
1249 if (signal_handlers[SIGQUIT] == (SignalHandler *) NULL)
1250 signal_handlers[SIGQUIT]=RegisterMagickSignalHandler(SIGQUIT);
1252 #if defined(SIGTERM)
1253 if (signal_handlers[SIGTERM] == (SignalHandler *) NULL)
1254 signal_handlers[SIGTERM]=RegisterMagickSignalHandler(SIGTERM);
1256 #if defined(SIGXCPU)
1257 if (signal_handlers[SIGXCPU] == (SignalHandler *) NULL)
1258 signal_handlers[SIGXCPU]=RegisterMagickSignalHandler(SIGXCPU);
1260 #if defined(SIGXFSZ)
1261 if (signal_handlers[SIGXFSZ] == (SignalHandler *) NULL)
1262 signal_handlers[SIGXFSZ]=RegisterMagickSignalHandler(SIGXFSZ);
1266 Instantiate magick resources.
1268 (void) ConfigureComponentGenesis();
1269 (void) PolicyComponentGenesis();
1270 (void) CacheComponentGenesis();
1271 (void) RegistryComponentGenesis();
1272 (void) ResourceComponentGenesis();
1273 (void) CoderComponentGenesis();
1274 (void) MagickComponentGenesis();
1275 #if defined(MAGICKCORE_MODULES_SUPPORT)
1276 (void) ModuleComponentGenesis();
1278 (void) DelegateComponentGenesis();
1279 (void) MagicComponentGenesis();
1280 (void) ColorComponentGenesis();
1281 (void) TypeComponentGenesis();
1282 (void) MimeComponentGenesis();
1283 (void) ConstituteComponentGenesis();
1284 (void) XComponentGenesis();
1288 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1292 % M a g i c k C o r e T e r m i n u s %
1296 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1298 % MagickCoreTerminus() destroys the MagickCore environment.
1300 % The format of the MagickCoreTerminus function is:
1302 % MagickCoreTerminus(void)
1305 MagickExport void MagickCoreTerminus(void)
1307 #if defined(MAGICKCORE_X11_DELEGATE)
1308 XComponentTerminus();
1310 ConstituteComponentTerminus();
1311 MimeComponentTerminus();
1312 TypeComponentTerminus();
1313 ColorComponentTerminus();
1314 #if defined(__WINDOWS__)
1315 NTGhostscriptUnLoadDLL();
1317 MagicComponentTerminus();
1318 DelegateComponentTerminus();
1319 MagickComponentTerminus();
1320 #if !defined(MAGICKCORE_BUILD_MODULES)
1321 UnregisterStaticModules();
1323 #if defined(MAGICKCORE_MODULES_SUPPORT)
1324 ModuleComponentTerminus();
1326 CoderComponentTerminus();
1327 ResourceComponentTerminus();
1328 RegistryComponentTerminus();
1329 CacheComponentTerminus();
1330 PolicyComponentTerminus();
1331 ConfigureComponentTerminus();
1332 RandomComponentTerminus();
1333 LocaleComponentTerminus();
1334 LogComponentTerminus();
1335 SemaphoreComponentTerminus();
1336 instantiate_magick=MagickFalse;
1340 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1344 + R e g i s t e r M a g i c k I n f o %
1348 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1350 % RegisterMagickInfo() adds attributes for a particular image format to the
1351 % list of supported formats. The attributes include the image format name,
1352 % a method to read and/or write the format, whether the format supports the
1353 % saving of more than one frame to the same file or blob, whether the format
1354 % supports native in-memory I/O, and a brief description of the format.
1356 % The format of the RegisterMagickInfo method is:
1358 % MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1360 % A description of each parameter follows:
1362 % o magick_info: the magick info.
1365 MagickExport MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1371 Delete any existing name.
1373 assert(magick_info != (MagickInfo *) NULL);
1374 assert(magick_info->signature == MagickSignature);
1375 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",magick_info->name);
1376 if (magick_list == (SplayTreeInfo *) NULL)
1377 return((MagickInfo *) NULL);
1378 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
1379 if (status == MagickFalse)
1380 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1381 return(magick_info);
1385 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1389 + S e t M a g i c k I n f o %
1393 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1395 % SetMagickInfo() allocates a MagickInfo structure and initializes the members
1396 % to default values.
1398 % The format of the SetMagickInfo method is:
1400 % MagickInfo *SetMagickInfo(const char *name)
1402 % A description of each parameter follows:
1404 % o magick_info: Method SetMagickInfo returns the allocated and initialized
1405 % MagickInfo structure.
1407 % o name: a character string that represents the image format associated
1408 % with the MagickInfo structure.
1411 MagickExport MagickInfo *SetMagickInfo(const char *name)
1416 assert(name != (const char *) NULL);
1417 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",name);
1418 magick_info=(MagickInfo *) AcquireMagickMemory(sizeof(*magick_info));
1419 if (magick_info == (MagickInfo *) NULL)
1420 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1421 (void) ResetMagickMemory(magick_info,0,sizeof(*magick_info));
1422 magick_info->name=ConstantString(name);
1423 magick_info->adjoin=MagickTrue;
1424 magick_info->blob_support=MagickTrue;
1425 magick_info->thread_support=(MagickStatusType) (DecoderThreadSupport |
1426 EncoderThreadSupport);
1427 magick_info->signature=MagickSignature;
1428 return(magick_info);
1432 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1436 + U n r e g i s t e r M a g i c k I n f o %
1440 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1442 % UnregisterMagickInfo() removes a name from the magick info list. It returns
1443 % MagickFalse if the name does not exist in the list otherwise MagickTrue.
1445 % The format of the UnregisterMagickInfo method is:
1447 % MagickBooleanType UnregisterMagickInfo(const char *name)
1449 % A description of each parameter follows:
1451 % o name: a character string that represents the image format we are
1455 MagickExport MagickBooleanType UnregisterMagickInfo(const char *name)
1457 register const MagickInfo
1463 assert(name != (const char *) NULL);
1464 if (magick_list == (SplayTreeInfo *) NULL)
1465 return(MagickFalse);
1466 if (GetNumberOfNodesInSplayTree(magick_list) == 0)
1467 return(MagickFalse);
1468 LockSemaphoreInfo(magick_semaphore);
1469 ResetSplayTreeIterator(magick_list);
1470 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1471 while (p != (const MagickInfo *) NULL)
1473 if (LocaleCompare(p->name,name) == 0)
1475 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1477 status=DeleteNodeByValueFromSplayTree(magick_list,p);
1478 UnlockSemaphoreInfo(magick_semaphore);